Acceder a las hojas de cálculo de Google con C # mediante la API de datos de Google

104

Tengo cierta información en Google Spreadsheets como una sola hoja. ¿Hay alguna forma en la que pueda leer esta información de .NET proporcionando las credenciales de Google y la dirección de la hoja de cálculo? ¿Es posible utilizar las API de datos de Google? En última instancia, necesito obtener la información de la hoja de cálculo de Google en un DataTable. ¿Cómo puedo hacerlo? Si alguien lo ha intentado, por favor comparta alguna información.

blitzkriegz
fuente
verifique mi respuesta stackoverflow.com/questions/48432846/…
Mike Darwish

Respuestas:

176

Según la guía del usuario de .NET :

Descargue la biblioteca cliente .NET :

Agregue estas declaraciones de uso:

using Google.GData.Client;
using Google.GData.Extensions;
using Google.GData.Spreadsheets;

Autenticar:

SpreadsheetsService myService = new SpreadsheetsService("exampleCo-exampleApp-1");
myService.setUserCredentials("[email protected]", "mypassword");

Obtenga una lista de hojas de cálculo:

SpreadsheetQuery query = new SpreadsheetQuery();
SpreadsheetFeed feed = myService.Query(query);

Console.WriteLine("Your spreadsheets: ");
foreach (SpreadsheetEntry entry in feed.Entries)
{
    Console.WriteLine(entry.Title.Text);
}

Dada una SpreadsheetEntry que ya ha recuperado, puede obtener una lista de todas las hojas de trabajo en esta hoja de cálculo de la siguiente manera:

AtomLink link = entry.Links.FindService(GDataSpreadsheetsNameTable.WorksheetRel, null);

WorksheetQuery query = new WorksheetQuery(link.HRef.ToString());
WorksheetFeed feed = service.Query(query);

foreach (WorksheetEntry worksheet in feed.Entries)
{
    Console.WriteLine(worksheet.Title.Text);
}

Y obtenga una alimentación basada en células:

AtomLink cellFeedLink = worksheetentry.Links.FindService(GDataSpreadsheetsNameTable.CellRel, null);

CellQuery query = new CellQuery(cellFeedLink.HRef.ToString());
CellFeed feed = service.Query(query);

Console.WriteLine("Cells in this worksheet:");
foreach (CellEntry curCell in feed.Entries)
{
    Console.WriteLine("Row {0}, column {1}: {2}", curCell.Cell.Row,
        curCell.Cell.Column, curCell.Cell.Value);
}
Kelly
fuente
3
¿Qué debo usar para el valor de cadena para el nuevo SpreadsheetsService (" exampleCo-exampleApp-1")? ¿Importa lo que ponga ahí? ¡Gracias!
Ian Davis
Obtenga una lista de hojas de cálculo: "Consulta de SpreadsheetQuery = new SpreadsheetQuery ();" debe leer "SpreadsheetFeed feed = myService.Query (query);" ¡Intenté editar pero no se cambiaron suficientes caracteres!
SQLBobScot
5
developers.google.com/google-apps/spreadsheets/authorize Importante: OAuth 1.0 ya no es compatible y se inhabilitará el 5 de mayo de 2015. Si su aplicación usa OAuth 1.0, debe migrar a OAuth 2.0 o su aplicación dejará de funcionar .
Kiquenet
1
este enlace, de @wescpy a continuación, me ayudó a encontrar información más relevante para mediados de 2016: googleappsdeveloper.blogspot.com/2016/05/…
joon
No funcionará después del 2020-03-03 ya que la biblioteca utilizada usa Google Sheets v3 API cloud.google.com/blog/products/g-suite/…
Ogglas
22

Escribí un contenedor simple alrededor de la biblioteca cliente .Net de Google , que expone una interfaz similar a una base de datos más simple, con tipos de registros fuertemente tipados. Aquí hay un código de muestra:

public class Entity {
    public int IntProp { get; set; }
    public string StringProp { get; set; }
}

var e1 = new Entity { IntProp = 2 };
var e2 = new Entity { StringProp = "hello" };
var client = new DatabaseClient("[email protected]", "password");
const string dbName = "IntegrationTests";
Console.WriteLine("Opening or creating database");
db = client.GetDatabase(dbName) ?? client.CreateDatabase(dbName); // databases are spreadsheets
const string tableName = "IntegrationTests";
Console.WriteLine("Opening or creating table");
table = db.GetTable<Entity>(tableName) ?? db.CreateTable<Entity>(tableName); // tables are worksheets
table.DeleteAll();
table.Add(e1);
table.Add(e2);
var r1 = table.Get(1);

También hay un proveedor LINQ que se traduce en los operadores de consulta estructurada de Google :

var q = from r in table.AsQueryable()
        where r.IntProp > -1000 && r.StringProp == "hello"
        orderby r.IntProp
        select r;
Mauricio Scheffer
fuente
@Kiquenet ¿Qué quieres decir? La última versión que veo de Google.GData. * Es 2.2.0 nuget.org/packages/Google.GData.Documents
Mauricio Scheffer
developers.google.com/google-apps/spreadsheets Versión 3.0 API (OAuth, etc.)
Kiquenet
@Kiquenet Avísame cuando Google actualice sus bibliotecas .NET. Pero creo que Google.GData. * 2.2.0 ya usa API v3.
Mauricio Scheffer
developers.google.com/google-apps/spreadsheets/authorize Importante: OAuth 1.0 ya no es compatible y se inhabilitará el 5 de mayo de 2015. Si su aplicación usa OAuth 1.0, debe migrar a OAuth 2.0 o su aplicación dejará de funcionar .
Kiquenet
17

(Junio-noviembre de 2016) La pregunta y sus respuestas ahora están desactualizadas porque: 1) Las API de GData son la generación anterior de las API de Google. Si bien no todas las API de GData han quedado obsoletos, todas las últimas API de Google no no utilizan el protocolo de datos de Google ; y 2) hay una nueva API de Google Sheets v4 (tampoco GData).

A partir de aquí, debe obtener la biblioteca cliente de las API de Google para .NET y usar la última API de hojas , que es mucho más potente y flexible que cualquier API anterior. Aquí hay una muestra de código C # para ayudarlo a comenzar. Consulte también los documentos de referencia de .NET para la API Sheets y la guía para desarrolladores de la biblioteca cliente de las API de Google .NET .

Si no es alérgico a Python (si lo es, simplemente finja que es un pseudocódigo;)), hice varios videos con ejemplos un poco más largos y más del "mundo real" del uso de la API de los que puede aprender y migrar a C # si lo desea :

wescpy
fuente
¿Se pueden utilizar estas herramientas para acceder también a archivos de Microsoft Excel?
2018
1
Desafortunadamente, tanto Microsoft como Google están fabricando productos competitivos que no se adhieren a un estándar común, por lo que debe encontrar sus propias herramientas para acceder a los archivos de Excel. Si es un desarrollador de Python, consulte python-excel.org . Para otros idiomas, deberá buscar en sus respectivas comunidades. Alternativamente, puede importar archivos de Excel a Google (usando la API de Drive) y luego usar la API de Hojas de cálculo para realizar las operaciones que desee. Las API de Google admiten una amplia variedad de idiomas ... consulte developers.google.com/api-client-library
wescpy
3

Puede hacer lo que pide de varias formas:

  1. Usando la biblioteca C # de hoja de cálculo de Google (como en la respuesta de Tacoman667) para obtener un ListFeed que puede devolver una lista de filas (ListEntry en el lenguaje de Google), cada una de las cuales tiene una lista de pares de nombre-valor. La documentación de la API de hoja de cálculo de Google ( http://code.google.com/apis/spreadsheets/code.html ) tiene información más que suficiente para comenzar.

  2. Usando la API de visualización de Google, que le permite enviar consultas más sofisticadas (casi como SQL) para buscar solo las filas / columnas que necesita.

  3. El contenido de la hoja de cálculo se devuelve como fuentes Atom, por lo que puede utilizar el análisis XPath o SAX para extraer el contenido de una fuente de lista. Hay un ejemplo de cómo hacerlo de esta manera (en Java y Javascript, aunque me temo) en http://gqlx.twyst.co.za .

tonys
fuente
2

Estoy bastante seguro de que habrá algunos SDK / kits de herramientas de C # en Google Code para esto. Encontré este , pero puede haber otros, así que vale la pena echarle un vistazo.

Steve
fuente
2

La respuesta más votada de @Kelly ya no es válida como dice @wescpy. Sin embargo, después de 2020-03-03 no funcionará en absoluto ya que la biblioteca utilizada usa Google Sheets v3 API.

La API de Google Sheets v3 se cerrará el 3 de marzo de 2020

https://developers.google.com/sheets/api/v3

Esto fue anunciado por Google el 10 de septiembre de 2019:

https://cloud.google.com/blog/products/g-suite/migrate-your-apps-use-latest-sheets-api

Nueva muestra de código para Google Sheets v4 API:

Ir

https://developers.google.com/sheets/api/quickstart/dotnet

y generar credentials.json. Entonces instalaGoogle.Apis.Sheets.v4 NuGet y pruebe la siguiente muestra:

Tenga en cuenta que recibí el error Unable to parse range: Class Data!A2:Econ el código de ejemplo pero con mi hoja de cálculo. Sheet1!A2:ESin embargo, cambiar a funcionó ya que mi hoja se llamó así. También trabajó con only A2:E.

using Google.Apis.Auth.OAuth2;
using Google.Apis.Sheets.v4;
using Google.Apis.Sheets.v4.Data;
using Google.Apis.Services;
using Google.Apis.Util.Store;
using System;
using System.Collections.Generic;
using System.IO;
using System.Threading;

namespace SheetsQuickstart
{
    class Program
    {
        // If modifying these scopes, delete your previously saved credentials
        // at ~/.credentials/sheets.googleapis.com-dotnet-quickstart.json
        static string[] Scopes = { SheetsService.Scope.SpreadsheetsReadonly };
        static string ApplicationName = "Google Sheets API .NET Quickstart";

        static void Main(string[] args)
        {
            UserCredential credential;

            using (var stream =
                new FileStream("credentials.json", FileMode.Open, FileAccess.Read))
            {
                // The file token.json stores the user's access and refresh tokens, and is created
                // automatically when the authorization flow completes for the first time.
                string credPath = "token.json";
                credential = GoogleWebAuthorizationBroker.AuthorizeAsync(
                    GoogleClientSecrets.Load(stream).Secrets,
                    Scopes,
                    "user",
                    CancellationToken.None,
                    new FileDataStore(credPath, true)).Result;
                Console.WriteLine("Credential file saved to: " + credPath);
            }

            // Create Google Sheets API service.
            var service = new SheetsService(new BaseClientService.Initializer()
            {
                HttpClientInitializer = credential,
                ApplicationName = ApplicationName,
            });

            // Define request parameters.
            String spreadsheetId = "1BxiMVs0XRA5nFMdKvBdBZjgmUUqptlbs74OgvE2upms";
            String range = "Class Data!A2:E";
            SpreadsheetsResource.ValuesResource.GetRequest request =
                    service.Spreadsheets.Values.Get(spreadsheetId, range);

            // Prints the names and majors of students in a sample spreadsheet:
            // https://docs.google.com/spreadsheets/d/1BxiMVs0XRA5nFMdKvBdBZjgmUUqptlbs74OgvE2upms/edit
            ValueRange response = request.Execute();
            IList<IList<Object>> values = response.Values;
            if (values != null && values.Count > 0)
            {
                Console.WriteLine("Name, Major");
                foreach (var row in values)
                {
                    // Print columns A and E, which correspond to indices 0 and 4.
                    Console.WriteLine("{0}, {1}", row[0], row[4]);
                }
            }
            else
            {
                Console.WriteLine("No data found.");
            }
            Console.Read();
        }
    }
}
Ogglas
fuente
¿Cómo puedo evitar tener que especificar la identificación del cliente / secretos y alcances? Ya hice el flujo de OAuth y tengo un token de acceso y un token de actualización (piense en el modo fuera de línea) y no quiero nada de esta basura adicional. No tengo acceso a la identificación del cliente y al secreto del cliente, ya que están en un servidor de retransmisión oauth al que no tengo acceso también en los servicios en segundo plano.
Blake Niemyjski
@BlakeNiemyjski Utilice el resto de API directamente, enlace: developers.google.com/sheets/api/reference/rest
Ogglas