# Working with DataSources in Code

## Content



Up to this point, we have been setting up data sources directly on the designer surface with very little code. **DataSource for Entity Framework** has made it very easy, but sometimes you want or need to do everything in code. [C1DataSource](/componentone/api/win/online-datasource/dotnet-framework-api/C1.Win.Data.Entity.4.8/C1.Win.Data.Entities.C1DataSource.html) makes this possible as well. Everything we did previously can be done at run time in code.

An obvious way to go about this would be to use the **ClientViewSource** object that we have, in effect, been setting up in the designer as elements of the **ViewSourceCollection** of a [C1DataSource](/componentone/api/win/online-datasource/dotnet-framework-api/C1.Win.Data.Entity.4.8/C1.Win.Data.Entities.C1DataSource.html), given that it can be created on its own without a [C1DataSource](/componentone/api/win/online-datasource/dotnet-framework-api/C1.Win.Data.Entity.4.8/C1.Win.Data.Entities.C1DataSource.html). We could, however, take a step further back and use a lower level class [ClientView](/componentone/api/win/online-datasource/dotnet-framework-api/C1.Data.Entity.4.8/C1.Data.ClientView-1.html)\<T>. This would provide full control over loading data from the server and, since it is derived from C1.LiveLinq.LiveViews.View\<T>, we can apply any LiveLinq operators to it. The ability to bind this to any GUI control whose datasource can be set to a View\<T> also means that we’ll end up with a fully editable view of our data.

Server-side filtering is, perhaps, the most common operation, because no one usually wants entire database tables brought to the client unrestricted. Earlier we saw how [C1DataSource](/componentone/api/win/online-datasource/dotnet-framework-api/C1.Win.Data.Entity.4.8/C1.Win.Data.Entities.C1DataSource.html) made it simple to perform without code, but now we’ll try it in run-time code.

To begin using [C1DataSource](/componentone/api/win/online-datasource/dotnet-framework-api/C1.Win.Data.Entity.4.8/C1.Win.Data.Entities.C1DataSource.html) in run-time code without a [C1DataSource](/componentone/api/win/online-datasource/dotnet-framework-api/C1.Win.Data.Entity.4.8/C1.Win.Data.Entities.C1DataSource.html), add a few lines to our project's main class to create a global client-side data cache. When we used [C1DataSource](/componentone/api/win/online-datasource/dotnet-framework-api/C1.Win.Data.Entity.4.8/C1.Win.Data.Entities.C1DataSource.html), it was created for us behind the scenes. Now we can create it explicitly using the following code:

DOC-DETAILS-TAG-OPEN

DOC-SUMMARY-TAG-OPEN

To write code in Visual Basic

DOC-SUMMARY-TAG-CLOSE

```vbnet
Imports C1.Data.Entities
 Public Class Program
     Public Shared ClientCache As EntityClientCache
     Public Shared ObjectContext As NORTHWNDEntities
     <STAThread()> _
     Shared Sub Main()
         ObjectContext = New NORTHWNDEntities
         ClientCache = New EntityClientCache(ObjectContext)
         Application.EnableVisualStyles()
         Application.SetCompatibleTextRenderingDefault(False)
         Application.Run(New MainForm())
     End Sub
 End Class
```

DOC-DETAILS-TAG-CLOSE

DOC-DETAILS-TAG-OPEN

DOC-SUMMARY-TAG-OPEN

To write code in C#

DOC-SUMMARY-TAG-CLOSE

```csharp
using C1.Data.Entities;
 static class Program
 {
     public static EntityClientCache ClientCache;
     public static NORTHWNDEntities ObjectContext;
     [STAThread]
     static void Main()
     {
         ObjectContext = new NORTHWNDEntities();
         ClientCache = new EntityClientCache(ObjectContext);
         Application.EnableVisualStyles();
         Application.SetCompatibleTextRenderingDefault(false);
         Application.Run(new MainForm());
 }
```

DOC-DETAILS-TAG-CLOSE

This code creates a single application-wide (static) **ObjectContext** and associates it with **EntityClientCache**. As noted previously in [The Power of Client Data Cache](/componentone/docs/win/online-datasource/DesignTimeFeatures/ClientSideCaching) topic, the ability to have a single context (and cache) for the entire application is a great simplification made possible by [C1DataSource](/componentone/api/win/online-datasource/dotnet-framework-api/C1.Win.Data.Entity.4.8/C1.Win.Data.Entities.C1DataSource.html).

To perform server-side filtering in run-time code, follow these steps:

1.  Add a new form using the project created to demonstrate [Customizing View](/componentone/docs/win/online-datasource/DesignTimeFeatures/CustomizingView).
2.  Add a grid (**dataGridView1**), a combo box (**comboBox1**), and a button (**btnSaveChanges**) to the form.
3.  Add the following code to the form class:
    
    DOC-DETAILS-TAG-OPEN
    
    DOC-SUMMARY-TAG-OPEN
    
    To write code in Visual Basic
    
    DOC-SUMMARY-TAG-CLOSE
    
    ```vbnet
    Imports C1.Data.Entities
     Imports C1.Data
     Public Class DataSourcesInCode
         Private _scope As EntityClientScope
         Public Sub New()
             InitializeComponent()
             _scope = Program.ClientCache.CreateScope()
             Dim viewCategories As ClientView(Of Category) = _scope.GetItems(Of Category)()
             comboBox1.DisplayMember = "CategoryName"
             comboBox1.ValueMember = "CategoryID"
             comboBox1.DataSource = viewCategories
             BindGrid(viewCategories.First().CategoryID)
         End Sub
         Private Sub BindGrid(categoryID As Integer)
             dataGridView1.DataSource =
                     (From p In _scope.GetItems(Of Product)().AsFiltered(Function(p As Product) p.CategoryID.Value = categoryID)
                      Select New With
                      {
                          p.ProductID,
                          p.ProductName,
                          p.CategoryID,
                          p.Category.CategoryName,
                          p.SupplierID,
                          .Supplier = p.Supplier.CompanyName,
                          p.UnitPrice,
                          p.QuantityPerUnit,
                          p.UnitsInStock,
                          p.UnitsOnOrder
                      }).AsDynamic()
         End Sub
    
         Private Sub btnSaveChanges_Click(sender As System.Object, e As System.EventArgs) Handles btnSaveChanges.Click
             Program.ClientCache.SaveChanges()
         End Sub
         Private Sub comboBox1_SelectedIndexChanged(sender As System.Object, e As System.EventArgs) Handles comboBox1.SelectedIndexChanged
             If comboBox1.SelectedValue IsNot Nothing Then
                 BindGrid(CType(comboBox1.SelectedValue, Integer))
             End If
         End Sub
     End Class
    ```
    
    DOC-DETAILS-TAG-CLOSE
    
    DOC-DETAILS-TAG-OPEN
    
    DOC-SUMMARY-TAG-OPEN
    
    To write code in C#
    
    DOC-SUMMARY-TAG-CLOSE
    
    ```csharp
    namespaceTutorialsWinForms
     {
         using C1.Data.Entities;
         using C1.Data;
         public partial class DataSourcesInCode : Form
         {
             private EntityClientScope _scope;
             public DataSourcesInCode()
             {
                 InitializeComponent();
                 _scope = Program.ClientCache.CreateScope();
                 ClientView<Category> viewCategories =_scope.GetItems<Category>();
                 comboBox1.DisplayMember = "CategoryName";
                 comboBox1.ValueMember = "CategoryID";
                 comboBox1.DataSource = viewCategories;
                 BindGrid(viewCategories.First().CategoryID);
             }
             private void comboBox1_SelectedValueChanged(object sender, EventArgs e)
             {
                 if (comboBox1.SelectedValue != null)
                     BindGrid((int)comboBox1.SelectedValue);
             }
             private void BindGrid(int categoryID)
             {
                 dataGridView1.DataSource =
                     (from p in _scope.GetItems<Product>().AsFiltered(
                          p => p.CategoryID == categoryID)
                      select new
                      {
                          p.ProductID,
                          p.ProductName,
                          p.CategoryID,
                          CategoryName = p.Category.CategoryName,
                          p.SupplierID,
                          Supplier = p.Supplier.CompanyName,
                          p.UnitPrice,
                          p.QuantityPerUnit,
                          p.UnitsInStock,
                          p.UnitsOnOrder
                      }).AsDynamic();
             }
             private void btnSaveChanges_Click(object sender, EventArgs e)
             {
                 Program.ClientCache.SaveChanges();
             }
         }
     }
    ```
    
    DOC-DETAILS-TAG-CLOSE
    
4.  Save, build and run your application. You should see similar results to those you saw in the [Server-Side Filtering](/componentone/docs/win/online-datasource/DesignTimeFeatures/ServerSideFiltering) example, the only difference being that this time we’ve implemented it all in code.

Let’s take a closer look at some of the code we’ve just written.

The private field **\_scope** is the form’s gateway to the global data cache. It is a pattern we recommend you follow in all the forms where you do not employ a [C1DataSource](/componentone/api/win/online-datasource/dotnet-framework-api/C1.Win.Data.Entity.4.8/C1.Win.Data.Entities.C1DataSource.html) component directly, as that does this for you automatically. It ensures that the entities the form needs stay in the cache while the form is alive, and that they are automatically released when all forms (scopes) holding them are released.

Creating a view showing all categories for the combo box is simple:

DOC-DETAILS-TAG-OPEN

DOC-SUMMARY-TAG-OPEN

To write code in Visual Basic

DOC-SUMMARY-TAG-CLOSE

```vbnet
Dim viewCategories As ClientView(Of Category) = _scope.GetItems(Of Category)()
```

DOC-DETAILS-TAG-CLOSE

DOC-DETAILS-TAG-OPEN

DOC-SUMMARY-TAG-OPEN

To write code in C#

DOC-SUMMARY-TAG-CLOSE

```csharp
ClientView<Category> viewCategories = _scope.GetItems<Category>();
```

DOC-DETAILS-TAG-CLOSE

To create the view to which the grid is bound that only provides those products associated with the chosen category in the combo box required one additional operator; AsFiltered(\<predicate>).

DOC-DETAILS-TAG-OPEN

DOC-SUMMARY-TAG-OPEN

To write code in Visual Basic

DOC-SUMMARY-TAG-CLOSE

```vbnet
From p In _scope.GetItems(Of Product)().AsFiltered(Function(p As Product) p.CategoryID.Value = categoryID)
```

DOC-DETAILS-TAG-CLOSE

DOC-DETAILS-TAG-OPEN

DOC-SUMMARY-TAG-OPEN

To write code in C#

DOC-SUMMARY-TAG-CLOSE

```csharp
from p in _scope.GetItems<Product>().AsFiltered(p => p.CategoryID == categoryID)
```

DOC-DETAILS-TAG-CLOSE

<br />

Note that when this query is executed, the result does not necessarily require a round trip to the server to retrieve the products requested. The cache is examined first to see if it already contains the requested data, either because the required data has already been requested once before within this form or from another form in the application. Or, possibly a completely separate query run elsewhere in the application had requested that all products be returned, so the cache would already have all the product data. Again, this is a fundamental strength of [C1DataSource](/componentone/api/win/online-datasource/dotnet-framework-api/C1.Win.Data.Entity.4.8/C1.Win.Data.Entities.C1DataSource.html). By providing your application with a global cache of data, its performance is continually improved throughout its lifetime.

Here we chose to create a new view, and bind the grid to it, every time the user selects a new category in the combo box (see the combo box’s **SelectedValueChanged** event). However, we could have avoided the need to create new views all the time and instead created one single view using a special **BindFilterKey**, which we'll learn more about in the [Simplifying MVVM](/componentone/docs/win/online-datasource/DesignTimeFeatures/SimplifyingMVVM2) topic.

So, in summary, we replicated in code what we did on the design surface with [C1DataSource](/componentone/api/win/online-datasource/dotnet-framework-api/C1.Win.Data.Entity.4.8/C1.Win.Data.Entities.C1DataSource.html) in [Server-Side Filtering](/componentone/docs/win/online-datasource/DesignTimeFeatures/ServerSideFiltering). We have even thrown in a little extra; we customized the fields shown in the grid columns as we did in [Customizing View](/componentone/docs/win/online-datasource/DesignTimeFeatures/CustomizingView) by adding a **Select** to our LiveLinq statement:

DOC-DETAILS-TAG-OPEN

DOC-SUMMARY-TAG-OPEN

To write code in Visual Basic

DOC-SUMMARY-TAG-CLOSE

```vbnet
Select New With
                     {
                         p.ProductID,
                         p.ProductName,
                         p.CategoryID,
                         p.Category.CategoryName,
                         p.SupplierID,
                         Supplier = p.Supplier.CompanyName,
                         p.UnitPrice,
                         p.QuantityPerUnit,
                         p.UnitsInStock,
                         p.UnitsOnOrder
                     }
```

DOC-DETAILS-TAG-CLOSE

DOC-DETAILS-TAG-OPEN

DOC-SUMMARY-TAG-OPEN

To write code in C#

DOC-SUMMARY-TAG-CLOSE

```csharp
select new
{
     p.ProductID,
     p.ProductName,
     p.CategoryID,
     CategoryName = p.Category.CategoryName,
     p.SupplierID,
    Supplier = p.Supplier.CompanyName,
    p.UnitPrice,
     p.QuantityPerUnit,
     p.UnitsInStock,
     p.UnitsOnOrder
 };
```

DOC-DETAILS-TAG-CLOSE

Had we just wanted the raw product data returned from the table without any special formatting, we could have simply said;

select p;