A practical tip: store the downloaded data locally after the first pull. Repeated requests for long histories are slow and may hit limits in the terminal, while local files make analysis much faster.
One thing that bit me early: the time column isn't really UTC. The terminal hands back epoch seconds stamped in server time, so pd.to_datetime with unit s gives you broker time labelled as UTC.
A typical New York close server sits two hours ahead of London, so the London open shows up as 10:00 in the dataframe. The exception is the week or two when UK and US clocks change on different dates, which matters now, with the UK falling back on 25 October and the US a week after. I subtract the offset straight after the pull and keep a proper UTC column next to the raw one.
For spread work I pull ticks with COPY_TICKS_INFO rather than ALL, since I only need bid and ask changes. The spread field in the bar data is one number per bar, so it hides exactly the spikes I'm measuring.
Agree on storing locally. I loop one day at a time and write each day to its own parquet file, so a failed request costs me a day instead of a month.
Small one: initialize returns False rather than raising when the terminal isn't logged in, so I check it and print last_error first. Have you found a reliable way to run it headless on a VPS?
FXS Prop Desk, the rate limit is what pushed me off long copy_rates calls. Pulling 50,000 M5 bars in one shot started returning None about once in five tries on my terminal, with last_error pointing at a timeout rather than a bad symbol.
I now pull at most 5,000 bars per call and stitch in pandas, then assert that the time delta between rows is exactly the timeframe. Any gap longer than one bar gets a row in a missing.csv so I do not silently backtest across a hole.
Session filters sit in pandas after the pull, not in the request. I keep a London mask as hour greater than or equal to 7 and less than 16 in proper UTC, and I rebuild that mask after every DST change instead of hard coding broker hours.
Gaps around Sunday open are the usual offenders. Do you drop those rows, forward fill, or keep them tagged so a session study can exclude them cleanly?