How to retrieve the table name with SubSonic 3? - subsonic3

Whit ol' good SubSonic 2 I was able to retrieve the name of the table I was querying:
.Schema.TableName
Now that I switched to SubSonic 3 I can't find any way to achieve the same goal.
I tend to avoid to hardcode the name of the table in the che source code, so if I change it the compiler throw me an exception.
(Note: yes, I'm using the new 'linq-like' syntax for most of the queries, but I dealing with a complex one and I think is better to follow the old manner).

Put following into structs.tt and you have Tables class ready with tables. You can use it like subsonic 2.0 that is Table.TableName.
public class Tables
{
<# foreach(var tbl in tables){
if(!ExcludeTables.Contains(tbl.Name))
{
#>
public static string <#=tbl.CleanName#> = "<#=tbl.Name#>";
<#
}
}
#>
}

Related

Bigquery struct introspection

Is there a way to get the element types of a struct? For example something along the lines of:
SELECT #TYPE(structField.y)
SELECT #TYPE(structField)
...etc
Is that possible to do? The closest I can find is via the query editor and the web call it makes to validate a query:
As I mentioned already in comments - one of the option is to mimic same very Dry Run call with query built in such a way that it will fail with exact error message that will give you the info you are looking for. Obviously this assumes your use case can be implemented in whatever scripting language you prefer. Should be relatively easy to do.
Meantime, I was looking for making this within the SQL Query.
Below is the example of another option.
It is limited to below types, which might fit or not into your particular use case
object, array, string, number, boolean, null
So example is
select
s.birthdate, json_type(to_json(s.birthdate)),
s.country, json_type(to_json(s.country)),
s.age, json_type(to_json(s.age)),
s.weight, json_type(to_json(s.weight)),
s.is_this, json_type(to_json(s.is_this)),
from (
select struct(date '2022-01-01' as birthdate, 'UA' as country, 1 as age, 2.5 as weight, true as is_this) s
)
with output
You can try the below approach.
SELECT COLUMN_NAME, DATA_TYPE
FROM `your-project.your-dataset.INFORMATION_SCHEMA.COLUMNS`
WHERE TABLE_NAME = 'your-table-name'
AND COLUMN_NAME = 'your-struct-column-name'
ORDER BY ORDINAL_POSITION
You can check this documentation for more details using INFORMATION_SCHEMA for BigQuery.
Below is the screenshot of my testing.
DATA:
RESULT USING THE ABOVE SYNTAX:

Doctrine Migration from string to Entity

I've an apparently simple task to perform, i have to convert several tables column from a string to a new entity (integer FOREIGN KEY) value.
I have DB 10 tables with a column called "app_version" which atm are VARCHAR columns type. Since i'm going to have a little project refactor i'd like to convert those VARCHAR columns to a new column which contains an ID representing the newly mapped value so:
V1 -> ID: 1
V2 -> ID: 2
and so on
I've prepared a Doctrine Migration (i'm using symfony 3.4) which performs the conversion by DROPPING the old column and adding the new id column for the AppVersion table.
Of course i need to preserve my current existing data.
I know about preUp and postUp but i can't figure how to do it w/o hitting the DB performance too much. I can collect the data via SELECT in the preUp, store them in some PHP vars to use later on inside postUp to write new values to DB but since i have 10 tables with many rows this become a disaster real fast.
Do you guys have any suggestion i could apply to make this smooth and easy?
Please do not ask why i have to do this refactor now and i didn't setup the DB correctly in the first time. :D
Keywords for ideas: transaction? bulk query? avoid php vars storage? write sql file? everything can be good
I feel dumb but the solution was much more simple, i created a custom migration with all the "ALTER TABLE [table_name] DROP app_version" to be executed AFTER one that simply does:
UPDATE [table_name] SET app_version_id = 1 WHERE app_version = "V1"

Find All Articles by Tag, Many-To-Many Relationship

The Problem
I have an Article entity in Doctrine, which has a many-to-many relationship with Tag. That is, an Article can be "tagged" with multiple tags, and they are bound together by the articles_tags table in the database.
Let us assume we wanted to find all Articles that are associated with given Tag. For the case of an example, let us say we wanted to find all Articles associated with the "cars" tag: an article about cars.
DQL as Opposed to SQL
Had this been regular SQL (or some flavor of it), I would have written a query in a similar manner to the following:
SELECT * FROM articles_tags WHERE tag_id IN (
SELECT id FROM tags WHERE name = 'cars')
This would give us all article_tags where there is a Tag that goes by the name "cars". Of course, should more than one tags be used in the query at one time, duplicate articles should also be thrown out: perhaps by using a GROUP BY. Furthermore, you could even get rid of the intermediary step of first selecting the article_tags and then going to the Articles, by writing a longer query.
From my current understanding of Doctrine, which ranges no more than a few days, you cannot directly reference intermediary tables; nor does it seem as though you can write subqueries using the DQL. As such, I am at a loss.
Any pointers as to where I should start writing the query from, or any information regarding how one in general might go about handling these types of database retrievals in an ORM such as Doctrine would be highly helpful!
Query in DQL is a bit simpler than pure SQL:
$q = "
SELECT a FROM AppBundle:Article
LEFT JOIN a.tags t
WHERE t.name = :tag";
$result = $em->createQuery($q)
->setParameter('tag', $tag)
->getResult()
;

References function in rails 4

I'm just not understand the new references() function in Rails 4
I'm reading the definition here : http://apidock.com/rails/ActiveRecord/QueryMethods/references
It's meaby a english problem, but it's still not clear for me.
What is the goal of this new feature? (code was working well without it before).
Must I always add a reference for each table of my includes() ?
Thanks
When using includes, Rails will usually load the results separately. For example, if you do
Post.includes(:comments)
it will issue a query to load the post(s) and then another to load the comments with the post_id of the post(s).
It will generate a join, if, for example, you want to do
Post.includes(:comments).where(comments: { user_id: 44})
Where one of the conditions is dependent on a related table. If, however, you were to use
Post.includes(:comments).where('comments.user_id = ?', 44)
You will get an error in Rails 4. Any time that you're referencing a relationship in a conditional using a SQL snippet, you will have to use references. To fix the above, we would do
Post.includes(:comments).where('comments.user_id = ?', 44).references(:comments)
The other option, of course, is to not use SQL snippets in your conditionals, like the second code example, but it's not always possible to avoid them.
I think this is intended for when you're eager loading an association and you're using a string condition. Because Rails doesn't want to have to parse raw SQL in where clauses to figure out what you're doing, so references is intended to make it more explicit what is going on in your query.
Group.includes(:users).where('users.first_name = ?', 'John')
You should get some kind of deprecation warning if you do this. But if you use a hash syntax you should not get the deprecation warning:
Group.includes(:users).where(users: { first_name: 'John' })
So to fix the deprecation warning on the first one, you would add references(:users) to it.
Group.includes(:users).where('users.first_name = ?', 'John').references(:users)
The query method references is used to indicate that an association is referenced by a SQL string and therefore be joined over being loaded separately. As of Rails 4.1, adding a string condition of an included reference will result in an exception being raised.
Here is an example that selects all Teams which have a member named Nishant:
>> Team.includes(:members).where('members.name = ?', 'Nishant')
SQLite3::SQLException: no such column: members.name: SELECT "teams".*
FROM "teams" WHERE (members.name = 'Nishant')
ActiveRecord::StatementInvalid: SQLite3::SQLException: no such column:
members.name: SELECT "teams".* FROM "teams" WHERE (members.name =
'Nishant')
...
To get the above example to work in Rails 4.1, we must include query method references with the name of the association to join
Team.includes(:members).where("members.name = ?", 'Nishant').references(:members)
However, if you were using the hash syntax with association conditions, it would still perform a LEFT OUTER JOIN without any exception being raised:
Team.includes(:members).where(members: { name: 'Nishant' })
Note that ordering string SQL snippets on included associations will still work the same way without the need
of references:
Team.includes(:members).order('members.name')
I hope this will help you.

Case sensitive LINQ to DataSet

I am having an issue with a strongly typed DataSet exhibiting case-sensitivity using LINQ to DataSet to retrieve and filter data. In my example project, I have created a strongly typed DataSet called DataSet1. It contains a single DataTable called Customers. To instantiate and populate, I create a couple of rows (notice the casing on the names):
// Instantiate
DataSet1 ds = new DataSet1();
// Insert data
ds.Customers.AddCustomersRow(1, "Smith", "John");
ds.Customers.AddCustomersRow(2, "SMith", "Jane");
Next, I can easily fetch/filter using the DataSet's built-in Select functionality:
var res1 = ds.Customers.Select("LastName LIKE 'sm%'");
Console.WriteLine("DataSet Select: {0}", res1.Length);
DataSet Select: 2
The trouble begins when attempting to use LINQ to DataSet to perform the same operation:
var res2 = from c in ds.Customers where c.LastName.StartsWith("sm") select c;
Console.WriteLine("LINQ to DataSet: {0}", res2.Count());
LINQ to DataSet: 0
I've already checked the instantiated DataSet's CaseSensitive property as well as the Customer DataTable's CaseSensitive property--both are false. I also realize that when using the Select methodology, the DataSet performs the filtering and the LINQ query is doing something else.
My hope and desire for this type of code was to use it to Unit Test our Compiled LINQ to SQL queries so I can't really change all the current queries to use:
...where c.LastName.StartsWith("sm", StringComparison.CurrentCultureIgnoreCase) select c;
...as that changes the query in SQL. Thanks all for any suggestions!
LINQ to DataSets still use normal managed functions, including the standard String.StartsWith method.
It is fundamentally impossible for these methods to be aware of the DataTable's CaseSensitive property.
Instead, you can use an ExpressionVisitor to change all StartsWith (or similar) calls to pass StringComparison.CurrentCultureIgnoreCase.
You could also use c.LastName.ToLower().StartsWith("sm" which will make sure you also retrieve lower cased entries. Good luck!