SELECT id, name, author
Quick, what is this query about? What's ironic is that I think you have it backwards: the columns are the implementation detail, not the table. The table is the context: you can't change that without having to change everything else. But columns are the last step, the selection after the filters, joins, etc. They can be changed at any time without affecting the logic.And the auto complete story is backwards. Often I know what columns I want, but I'm not clear what table I need to get them from. Such that, if you make a smarter suggest in the from to only include tables that have the columns, I'd be much happier.
I further assert that if your database is filled with "Id" and "name" columns, instead of "department_name" and similar, you are probably as likely to mess up a join as any benefit you get from the name being short. (And really, what advantage is there in short names nowadays?)
That all said. I worded my take too strongly. My point should have been that auto suggest should not be confined in either direction.
When I'm trying to query stuff, the first question is "which service's database is that in?", so I can guess "user_service" (or whatever I think it is called), but I have no idea what they call anything in their schema, but now that the autocomplete system knows what table I'm interested in, it can help me figure that out.
That said, I want to be clear that I think both methods are valid and work.
I can think back to projects / companies where this may have been different, basically just with fewer different distinct schemas, but it just isn't my recent experience.
(I appreciate your magnanimity in these later comments by the way.)
> The table is the context: you can't change that without having to change everything else.
Except even in the provided single-table example this isn't true - you're getting subselected/CTEd results. No functional joins are demonstrated unfortunately.
For example:
from employees
left_join positions [id=employee_id]
...is equivalent to...
SELECT * FROM employees LEFT JOIN positions ON id = employee_id
No data is selected from positions in either example, and it's unclear on why we're joining that table (other than just for the heck of it). It's not a workable example. FROM articles
What fields am I expecting in the resultset? Sure I have some context, I know it'll be about articles, but I have no idea what actual data I care about.You're arguing that:
FROM articles
SELECT id, name, author
Is substantially superior to: SELECT id, name, author
FROM articles
I don't see them as markedly different with such a small example.
HOWEVER, where the difference comes in is the "at a glance what am I getting in my resultset" data that is much easier to see in the latter, second easiest in the former, and not at all present in the linked article.I think what this boils down to is what you (any reader, not you specifically) individually expect to need knowledge of when you're writing SQL. In most cases when sitting down to write a brand new piece of code to pull some data from the database, putting the list of tables involved in the query first matters most to some, whereas putting the list of fields to expect in the resultset matters most to others (I put myself in this camp).
For what it's worth, as I've stated elsewhere while I don't prefer it and would find it annoying to debug personally, I do recognize that the idea of SQL that allows you to list FROM / JOIN / etc. first is very appealing to some. What I think is completely off is the near-obfuscation of the examples in the linked article.
Of course not, because we're talking about a fundamental change in syntax that affects more than just two-line queries. PRQL puts the SELECT clause practically at the end of the query, after every join, filter, and aggregate. If you only care about the output, that's cool too: just look at the end. But if I want to understand a query in SQL, I have to read the entire thing backwards, clause by clause! By contrast, if the SELECT is at the end, that's not much of a problem.
Now you'll come back and say "but it's the same if you care about context: just look at the end!" And that's where we differ. I care more about writing, debugging, and understanding queries, whereas you think it's more important that the column names are up front, even if it makes understanding a nontrivial query much, much harder.
If you want an interesting example of how a query language built for developer experience and autocompletions looks definitely check it out!.
1. What tables are being pulled from? This speaks to the potential domain of the query. 2. What data is being selected (I can now know what is or isn't being pulled from the aforementioned tables...) 3. What operations, aggregations, groupings, etc. are being performed to work on the pulle data
Of course from vs select ordering is completely arguable, but my thinking process seems to follow that of the auto complete--in other words that my cognitive load of looking at the select statement is lessened when I know from what the columns are being selected.
It also follows (at least to me) the mental process of writing the query. First look at the tables, then decide what columns, then decide what functions to apply.
The language should be right for human understanding, not automated mad-lib generation.
I understand this is just an opinion but it's an opinion held by everyone in my org who writes both.
Theoretical correctness loses to pragmatism a lot and I'd read the KQL every day. Look at the examples at https://docs.microsoft.com/en-us/azure/data-explorer/kusto/q... - look at the examples at https://docs.microsoft.com/en-us/azure/data-explorer/write-q... and tell me they're not more readable than comparable SQL?
(I can see the result type both by hovering on the query but also by just looking at the end of it - and in SQL most of the SELECTed items in complex queries are from subqueries anyway - at least in my use case)
If you want nice autocomplete too, that's fine, but if there is a tradeoff, human understanding is the primary concern.
C#'s LINQ (really powerful tool similar to SQL) works the same way
look:
var list = new List<int>{1,2,3}
var extracted = list
.............................Where(x => x > 1)
.............................Select(x => $"my number: {x})
.............................ToList();
or
var extarcted =
........................from x in list
........................where x > 1
........................select $"my number: {x};
Toilets are absolutely designed to make the dispenser placement convenient. You just don’t think about it because 95% of toilets get it right, so it just doesn’t bother you that much that it can be wrong.
In SQL, some decisions are right about 10% of the time and are annoying and awkward the other 90%.
That’s why the order matters. Because everything else got it right.
Then, the ide could basically fill my from out for me, based on what I'm asking for. Can even suggest what join I will need, if I list columns from multiple tables.
Every table has more than one column
So there's always more columns to remember than tables and generally tables are pretty easy like user invoices blabla
I worked with systems that had like 500 tables and some of them with 20-50 columns
you really want good intellisense in such a environment
Good intelligent suggestions is, of course, helpful. And I agree that suggesting one of 500 is easier than the other. That said, neither is hard for a computer. And even asking friends what table I want will often be done with starting with the actual columns I want.
if you start query with
SELECT MiddleName then you could receive auto complete thats adds "FROM Users" and moves your cusor after MiddleName.
if you start query with
FROM Users SELECT _ and know intellisense drops list of columns
Where is the data coming from? Employees table. What's coming out? 20 rows of sum_gross_cost.
What could improve this is function signatures. It's kind of nice to have the whole abstraction up top...like an abstract.
For example:
select @@version from @@special
select version from dual
select @@versionOne idea would be along the lines of a function prototype: a declaration, up front, about the columns and types that a query is expected to return. It's a good place to put documentation, it's redundant information which should protect against mistakes but not so redundant that it would be too taxing - the author should know what the query returns. The prototype would only be used for validation of column names and types.
Another idea would be requiring the last element in a query to be a projection, a bit like the return statement in a function body: here's what I'm returning out of the grand set of symbols available (e.g. via various joins) in scope from previous operations in the flow.
Reading the comment however, it would seem that `let` adds columns which are implicitly returned in the order they are defined.
I do see benefits in this, and can imagine pitfalls. Hard to judge without kicking the tires.
Update: It's quite possible we saw different syntax!
https://news.ycombinator.com/item?id=30063266
Without the `let` I would imagine having trouble reading it as well, I'm not sure if that would go away with familiarity but my instinct is that it's a useful addition.
While it inherently feels unnatural I do agree with the others here that the context is actually easier to understand once over the initial uncomfort.
In SQL, where _from_ is placed at the end, we are essentially writing equivalent of 'property.object'; eg.: name.person, age.person
To your point - a solid IDE will show you what's being processed at each line (or returned, if the cursor is on the last line) - in an autocomplete window or a side panel.
I want to understand what exactly the query returns, not the implementation detail of the source of this data (that can later be changed).
Literally first example from page - I have no idea what is being returned:
of course, similar things are happening to SQL too, with CTEs becoming more widespread and "real" list of the columns hidden somewhere inside, but it's still parseable