In short: Excel can't open a .sav file. You convert it to CSV first, with R, Python or a free program such as PSPP, jamovi or JASP, and then import the CSV into Excel. The conversion costs you something: a CSV keeps either the codes or the value labels, and it drops the variable labels, the missing-value definitions and the weight setting. If you only want to see what a file contains, you don't need to convert anything.
Only want to look inside? The free SPSS Inspector opens the .sav in your browser and shows every variable with its labels and frequencies. Nothing is uploaded and nothing needs installing.
What a .sav file holds that a spreadsheet doesn't
A .sav file is SPSS's own data format. Besides the table of answers it stores metadata: a label for every variable ("q7" is "How likely are you to recommend us?"), a label for every value (1 is "not at all likely"), the codes that count as missing, measurement levels and, often, which variable weights the sample.
A spreadsheet has one cell per value and a header row, which leaves no place for most of that. Every way into Excel therefore makes the same trade, and it helps to decide up front what you need: the labels, so people can read the table, or the codes, so you can calculate with them.
Convert with R
R reads .sav files with the haven package. as_factor() swaps the codes for their value labels, so you choose which version to write out:
install.packages("haven")
library(haven)
data <- read_sav("survey.sav")
# codes, for calculating
write.csv(zap_labels(data), "survey-codes.csv", row.names = FALSE, fileEncoding = "UTF-8")
# value labels, for reading
write.csv(as_factor(data), "survey-labels.csv", row.names = FALSE, fileEncoding = "UTF-8")
If you stay in R afterwards, keep the data as it is. haven keeps the variable labels as attributes, and as_factor() turns single columns into labelled factors whenever you need them.
Convert with Python
pandas reads .sav files through the pyreadstat package. Install both with pip install pandas pyreadstat. By default read_spss() replaces the codes with their value labels:
import pandas as pd
df = pd.read_spss("survey.sav") # value labels
df.to_csv("survey-labels.csv", index=False, encoding="utf-8")
codes = pd.read_spss("survey.sav", convert_categoricals=False) # codes
codes.to_csv("survey-codes.csv", index=False, encoding="utf-8")
For the variable labels, call pyreadstat directly. pyreadstat.read_sav() returns the data plus a metadata object, and meta.column_names_to_labels maps every column to its question text, which you can write into a second sheet as a small codebook.
Convert without code: PSPP, jamovi, JASP
Three free desktop programs open .sav files directly. jamovi and JASP have a point-and-click interface and export the data as CSV from the File menu. PSPP looks and works like SPSS; to export, run one line of syntax:
SAVE TRANSLATE /OUTFILE='survey.csv' /TYPE=CSV /FIELDNAMES /CELLS=LABELS.
/CELLS=LABELS writes the value labels, and /CELLS=VALUES writes the codes. All three programs keep the file on your computer.
Open the CSV in Excel
Double-clicking a CSV lets Excel guess the delimiter and the encoding, and it often guesses wrong: accented letters turn into garbage, and leading zeros vanish from postcodes. Import it instead via Data > From Text/CSV, choose UTF-8 as the file origin and check the preview before loading. If the characters are already broken, the article on fixing garbled characters explains what happened and how to repair it.
Then check the missing values. Codes like 99 for "no answer" arrive as ordinary numbers, and Excel includes them in every average. Filter or delete them per question before you calculate anything.
Why not an online converter?
Many of the results for "sav to csv" are websites that convert the file for you. They work, but they upload the raw data to a server whose owner, location and retention rules you don't know. Survey files often contain postcodes, ages, free-text answers and sometimes email addresses. Under the GDPR, handing that data to an unknown service needs a legal basis and a processing agreement, and you have neither. The local options above take five minutes longer and avoid the question.
Which way fits
| You want to… | Use |
|---|---|
| see what the file contains | SPSS Inspector, in the browser |
| convert once, without code | jamovi, JASP or PSPP |
| convert repeatedly or in a pipeline | R (haven) or Python (pandas, pyreadstat) |
| analyse it with crosstabs, weights and charts | skip Excel and import the .sav into an analysis tool |
The last row is where many conversions turn out to be a detour. People export to Excel because they want a table by age group or a chart for a slide, and then rebuild the weighting and the labels by hand. DataLion imports the .sav with variable labels, value labels, missing values and the weight variable, builds crosstabs and dashboards from it, and still exports to Excel when someone needs a spreadsheet. How the analysis works step by step is in the guide How to analyse an SPSS file without SPSS.
Next step
Open the file in the SPSS Inspector first and note which codes mean "no answer" and whether there is a weight variable. Then pick the route from the table above. If the plan is a report rather than a spreadsheet, import the file into DataLion and start on the Free starter plan.