Azure Remote Tables And Entity Framework: Join two tables - entity-framework

I read through some answeres here, but they dont seem to apply my usecase.
I have a a few tables running on Azure Mobile Apps Backend, I can query them just fine with entity framework.
I know that I could do two queries and just join my results on client side, but Im sure there is a better way.
My issue is however, that I have a table inside my middleware, and then a dataservice with a remote model class that I use to query data from my service. This is how I would query a User by Email:
public async Task<IEnumerable<UserItem>?> GetItemByEmail(string email)
{
await InitializeAsync();
try
{
return await _table.GetAsyncItems().Where(x => x.Email == email).ToListAsync();
}
catch (Exception e)
{
return null;
}
}
The issue however is, that this only works on the one table (UserItemTable) which is referencend in _table.
Now there is no reference to a second table with which I wanna join.
Maybe this isnt the right place to do this inside the RemoteTable Controllers?
Any help would be appreciated.

Related

Access Control Filtering of Query before its sent to Prisma server/DB

Right now I am using accesscontrol to manage the ACL and it is working great. It looks something like this:
const methods = {
async update(parent, { data }, ctx, info) {
const acUpdate = ac.can('role').updateOwn('model')
if (! acUpdate.granted) throw new ACError()
const filtered = acUpdate.filter({ ...data })
return await ctx.db.mutation.updateOrganization({
data: filtered,
where: { id }
}, info)
}
}
However, on a Query method from GraphQL I don't know how to filter the requests to the DB. For example, on a nested query it may look like this:
{
model {
id
name
user {
id
name
pictures {
id
name
}
}
}
}
So on the resolver it would check if they have access to Model, then it would send the request to the Prisma server without filtering the GQL schema. In this scenario let's say that the user has access to read model but not user. Ideally I'd like to do a permission.filter(...) on the actual request schema (info?) before sending it to Prisma. Have any of you solved this? Of course its possible to filter the request after it has resolved, but that level of computation is not necessary and can cause issues if abused.
I found out this is the topic I was addressing in one of my issue responses because I thought it was asked there. I recognize now that I must have confused it with this one being open in one of the tabs in the back.
https://github.com/maticzav/graphql-shield/issues/113#issuecomment-423766569
I think that the second part of my response concerns you the most. I hope you find it helpful! 🙂
I was having the exact same problem and i am now solving it by using prisma client for making the requests to prisma. Prisma client only queries one level deep each time so you get full control of the resolvers also in nested queries.
See https://stackoverflow.com/a/53703140/1391050

Raw SQL with Entity Framework

I am trying to write a simple raw query with Entity Framework to my database:
[ResponseType(typeof(Customer))]
[Route("name/{name}")]
[HttpGet]
public List<Customer> GetCustomerName(string name)
{
//var results = db.Customers.SqlQuery("SELECT Name from dbo.Customer").Where(p => p.Name.Equals(name)).ToList();
var results = db.Customers.SqlQuery("SELECT Name from dbo.Customer WHERE Name = #Name",new SqlParameter("#Name",name)).ToList();
//var results = db.Customers.Where(p => p.Name.Equals(name));
return results;
}
The last Entity Framework query works just fine, but I want to do raw SQL to get something back simple because I have never gotten raw SQL with Entity Framework to work and I see all of these examples where people says it works for them. The top 2 var results do not work I get this error any help would be greatly appreciated. I am a Web API 2 newbie and I am just trying to learn it
So the error says a member of the type AccrRevAcct does not have a corresponding column. I am not sure what that means AccrRevAcct is a column on my database but so is Name and I just want the Name of my customer.
http://localhost:61280/api/Customers/name/1st MIDAMERICA CREDIT UNION
This is the call I make to my server and like I said it returns fine with the 3rd statement but that isn't raw SQL like I want to achieve. I only want to do this because I have some developers saying they can't get everything to work in EF I personally like it and haven't ran into this problem I want to show them fine just drop to raw SQL, but I need to show them I can make it work first lol.
If you are using SqlQuery on the DbSet you have to return a full instance. If you want to reshape the data like you are doing you need to use the SqlQuery<T> on the db.Database instead.
Example from https://msdn.microsoft.com/en-us/library/jj592907(v=vs.113).aspx
using (var context = new BloggingContext())
{
var blogNames = context.Database.SqlQuery<string>(
"SELECT Name FROM dbo.Blogs").ToList();
}
Honestly I think you are trying to solve the wrong problem. The last query is the one you should be using. If your developers can't get EF to work that is what needs to be fixed.

How to execute scalar query on an IMobileServiceSyncTable?

I'm moving my app over from Sqlite-Net to Azure Mobile Services and I'm adding offline sync capabilities.
I'm unsure how to execute arbitrary queries. This is what I have for Sqlite-Net:
var newestDate = await this.connection.ExecuteScalarAsync<DateTime> ("SELECT MAX(TimeStamp) FROM SupplyData");
How can I run this query against my IMobileServiceSyncTable instance?
There is a CreateQuery() method but it does not take any parameters.
Is there any reason you can't use LINQ?
// This query filters out completed TodoItems and items without a timestamp.
List<TodoItem> items = await todoTable
.Where(todoItem => todoItem.Complete == false)
.ToListAsync();
Reference: https://azure.microsoft.com/en-us/documentation/articles/app-service-mobile-dotnet-how-to-use-client-library/#filtering
The alternate to this is to call a custom API. In ASP.NET backends, this is just a WebAPI that uses the underlying Entity Framework stuff. See https://azure.microsoft.com/en-us/documentation/articles/app-service-mobile-dotnet-backend-how-to-use-server-sdk/#how-to-define-a-custom-api-controller For Node.js backends (or Easy Tables / Easy API), see the following sample code: https://github.com/Azure/azure-mobile-apps-node/tree/master/samples/custom-api-sql-stmt

Use custom query for built-in entities in liferay 6.1?

I have read many posts about creating service layer in liferay. I was able to build a service layer and custom query sample project in eclipse. However, all of the examples I got so far is about adding new entities and performing CRUD actions on those new entities.
I want to ask is it possible to use custom query with built-in entities?. For example, I want to use custom query with JounalArticle, AssetEntry, and so on.
If that possible, how can I do that. Please give me some hints or examples.
(I have tried dynamic queries with sub queries but they do not meet my requirements)
If someone is interested:
In the XXXLocalServiceImpl you can add:
public List<JournalArticle> getArticles(String username) {
Session session = xxxPersistence.openSession();
try {
String sql = "SELECT * FROM journalarticle ja WHERE ja.userName like '%"+username+"%'";
SQLQuery query = session.createSQLQuery(sql);
return query.list();
}finally {
session.close();
}
}
rerun your service builder and you can use form XXXLocalServiceUtil.getArticles("Test Test")
Using service builder: create database portlets

MVC 1.0 + EF: Does db.EntitySet.where(something) still return all rows in table?

In a repository, I do this:
public AgenciesDonor FindPrimary(Guid donorId) {
return db.AgenciesDonorSet.Include("DonorPanels").Include("PriceAdjustments").Include("Donors").First(x => x.Donors.DonorId == donorId && x.IsPrimary);
}
then down in another method in the same repository, this:
AgenciesDonor oldPrimary = this.FindPrimary(donorId);
In the debugger, the resultsview shows all records in that table, but:
oldPrimary.Count();
is 1 (which it should be).
Why am I seeing all table entries retrieved, and not just 1? I thought row filtering was done in the DB.
If db.EntitySet really does fetch everything to the client, what's the right way to keep the client data-lite using EF? Fetching all rows won't scale for what I'm doing.
You will see everything if you hover over the AgenciesDonorSet because LINQ to Entities (or SQL) uses delayed execution. When the query is actually executed, it is just retrieving the count.
If you want to view the SQL being generated for any query, you can add this bit of code:
var query = queryObj as ObjectQuery; //assign your query to queryObj rather than returning it immediately
if (query != null)
{
System.Diagnostics.Trace.WriteLine(context);
System.Diagnostics.Trace.WriteLine(query.ToTraceString());
}
Entity Set does not implement IQueryable, so the extension methods that you're using are IEnumerable extension methods. See here:
http://social.msdn.microsoft.com/forums/en-US/linqprojectgeneral/thread/121ec4e8-ce40-49e0-b715-75a5bd0063dc/
I agree that this is stupid, and I'm surprised that more people haven't complained about it. The official reason:
The design reason for not making
EntitySet IQueryable is because
there's not a clean way to reconcile
Add\Remove on EntitySet with
IQueryable's filtering and
transformation ability.