Скопируйте все строки в другую таблицу в хранилище таблиц Azure.

Каков наилучший способ скопировать все строки из одной таблицы в другую?
Я попробовал следующий код, чтобы получить все строки в таблице:

    TableServiceContext _dataContext;
    public IEnumerable<T> GetAllEntities()
    {
        IQueryable<T> query = null;
        try
        {
            query = _dataContext.CreateQuery<T>(_tableName);
        }
        catch (Exception ex)
        {

        }
        return query.ToArray();
    }

но он не получает строк более 900. У меня несколько сотен тысяч строк.
Обновленный код:

 public class TableRepository<T> : IRepository<T> 
    where T : TableEntity
{
    protected readonly string _tableName;
    protected readonly TableServiceContext _dataContext;
    protected readonly CloudTable _tableReference;

    public TableRepository(string tableName, CloudTableClient tableClient)
    {
        _tableName = tableName;
        _dataContext = tableClient.GetTableServiceContext();
        _tableReference = tableClient.GetTableReference(tableName);
        _dataContext.ResolveType = ResolveEntityType;
        _dataContext.MergeOption = System.Data.Services.Client.MergeOption.NoTracking;
    }

    public IEnumerable<T> GetAllEntities()
    {
        List<T> allEntities = new List<T>();
        try
        {
            Microsoft.WindowsAzure.Storage.Table.TableContinuationToken tableContinuationToken = null;
            do
            {
                var queryResponse = _tableReference.ExecuteQuerySegmented<T>(null, tableContinuationToken, null, null);
                tableContinuationToken = queryResponse.ContinuationToken;
                allEntities.AddRange(queryResponse.Results);
            }
            while (tableContinuationToken != null);

        }
        catch (Exception ex)
        {
            throw new DALException(_tableName,_dataContext.BaseUri.OriginalString, "An error occured while querying data", ex);
        }
        return allEntities;
    }

}

но с ошибкой:

Ошибка 121 «T» должен быть неабстрактным типом с общедоступным конструктором без параметров, чтобы использовать его в качестве параметра «TElement» в универсальном типе или методе «Microsoft.WindowsAzure.Storage.Table.CloudTable.ExecuteQuerySegmented».


person Srinivas    schedule 22.08.2013    source источник


Ответы (1)


Причина, по которой вы получаете только 900 результатов, заключается в том, что вы сталкиваетесь с токенами продолжения. По умолчанию один запрос к службе таблиц возвращает не более 1000 сущностей. Это может быть меньше 1000 сущностей (и даже 0), но не более 1000. Если доступно больше сущностей, то служба таблиц возвращает continuation token, который следует использовать для выборки следующего набора сущностей.

Таким образом, ваш код должен искать токен продолжения и продолжать извлекать объекты до тех пор, пока токен времени не будет возвращен службой таблиц. Взгляните на пример кода ниже:

private IEnumerable<T> FetchAllEntities()
{
    List<T> allEntities = new List<T>();
    CloudStorageAccount storageAccount = CloudStorageAccount.DevelopmentStorageAccount;
    CloudTable table = storageAccount.CreateCloudTableClient().GetTableReference("MyTable");
    Microsoft.WindowsAzure.Storage.Table.TableContinuationToken tableContinuationToken = null;
    do
    {
        var queryResponse = table.ExecuteQuerySegmented<T>(null, tableContinuationToken, null, null);
        tableContinuationToken = queryResponse.ContinuationToken;
        allEntities.AddRange(queryResponse.Results);
    }
    while (tableContinuationToken != null);
    return allEntities;
}

Обновить

Для вашей ошибки попробуйте изменить следующее

public class TableRepository<T> : IRepository<T> 
    where T : TableEntity

to

public class TableRepository<T> : IRepository<T> 
    where T : TableEntity, new()

обратите внимание на добавление new() после TableEntity.

person Gaurav Mantri    schedule 22.08.2013
comment
Я получаю эту ошибку. Ошибка 121 «T» должна быть неабстрактным типом с общедоступным конструктором без параметров, чтобы использовать его в качестве параметра «TElement» в универсальном типе или методе. - person Srinivas; 22.08.2013
comment
Обновил и мой ответ :) - person Gaurav Mantri; 22.08.2013