Using AI for Data Conversion

Tools
I'm sure I've never mentioned that I'm an amateur radio operator. Like Vegans and Cross Fitters, we tend to be shy and withdrawn about our predilections. BWA-HA-HA! Ok, like Vegans and Cross Fitters, you can't get a ham to shut up about playing radio. Anyhoo, I've been experimenting with a brand new, and somewhat buggy, radio, the Baofeng DM-32UV. I'm writing this blog post about how I am using an AI for data conversion to make it a little easier to use this radio. The Problem The DM-32 is a Digital Mobile Radio (DMR) as well as an analog radio. You can follow the link to understand all that DMR represents when talking radios. I want to focus on the fact that you have to program the behaviors into a…
Read More

Extended Events: Avoid the XML

SQL Server, Tools
One story I hear over and over goes like this: I tried setting up Extended Events, but then I saw the output was XML so I stopped. Look, I get it. I don't like XML either. It's a pain to work with. It's actively difficult to write queries against it. If there weren't a ton of ways to avoid the XML, yeah, I would never advocate for Extended Events. However, here we are, I have ten pages of blog posts that at least mention Extended Events. Why? Because I avoid the XML (most of the time). Lots of other people do as well. You can too. Let's see how. Live Data Window I have a video that goes into this in detail right here. But the core concept is simple.…
Read More

Query Store as an Upgrade Tool

SQL Server, Tools
There are a lot of uses for Query Store, but one of the most interesting is as an upgrade tool. We all know that upgrades in SQL Server can be more than a little bit nerve wracking. No matter how much you tested stuff in lower environments, deploying an update to production might result in performance issues as your code hits a regression. This is even more true when upgrading from versions of SQL Server prior to 2014 to anything 2014 and above. That's because of the new cardinality estimation engine introduced in 2014. Most queries won't notice it. Some queries will benefit from the better estimates. A few, problematic, queries will suffer. This is where Query Store can be used as an upgrade tool. The Steps We're going to…
Read More

Extended Events Capturing the T-SQL of Prepared Statements

SQL Server, T-SQL, Tools
I asked this question myself: Is there a way to use Extended Events to capture the T-SQL of a prepared statement? Why would I be concerned with prepared statements? Wouldn't sql_batch_completed and rpc_completed cover us? Well, no. What happens when you use sp_prepare? What happens when you're using an ORM tool that's using prepared statements? You may see queries that look like this: EXEC sp_execute 5, 48766; What the heck code is that executing? Let's find out. sp_statement_completed Here's a set of sample code that I swiped from Microsoft (they don't mind, but, full attribution like a good citizen, you'll find it here): DECLARE @P1 int; EXEC sp_prepare @P1 output, N'@Param int', N'SELECT * FROM Sales.SalesOrderDetail AS sod INNER JOIN Production.Product AS p ON sod.ProductID = p.ProductID WHERE SalesOrderID =…
Read More

Extended Events Misperceptions: Profiler is Easier, Part 2

SQL Server, Tools
I wrote a short blog post about the misperception that Profiler was easier than Extended Events when it came to the core concept of "click, connect, BOOM, too much data". Go read it if you like, but I don't think it's actually an effective argument for how much easier Extended Events is than Profiler. Here, we're going to drill down on that concept in a real way. Let's start with a little clarification. I'm going to be a little lazy with my language. Trace is a scripted capture of events on a server. Profiler is a GUI for consuming a Trace, either live or from a file, and for creating Trace events. However, almost everyone refers to 'Profiler' when they mean either Trace or Profiler. I may do the same…
Read More

Microsoft Tools That Help Query Tuning

SQL Server, T-SQL, Tools
Query tuning is not easy. In fact, for a lot of people, you shouldn't even try. It's much easier to buy more, bigger, better hardware. Yeah, the query is still slow on newer, faster hardware, but not as a slow as it was. However, sooner or later, you're going to have to start to spend time fixing queries. In fact, you can find that fixing queries actually is more cost effective than buying more hardware. The problem is, query tuning is not easy. So, what do you do? Microsoft Can Help There are a number of tools available to you, right now, provided by Microsoft that can help you better and more easily tune your queries. This ranges from extended events to query store, and absolutely includes execution plans and…
Read More

Your First Jupyter Notebook

Tools
In April, I said I was going to start learning Jupyter Notebooks. It's November. Let's get going with your first Jupyter Notebook. A quick aside before we start. I think one of the huge strengths that is going to come out of these things is as a runbook. You can share a notebook with someone, they can run the queries on it against their own systems and return the book, with the results to you. That's going to be extremely useful as a troubleshooting tool, but has all sorts of other functionality as well. I strongly suggest you start learning these things, as I am. Azure Data Studio There are a number of ways to create and consume Jupyter Notebooks, but I want to focus on the functionality around data…
Read More

Which Query Used the Most CPU? Implementing Extended Events

SQL Server, T-SQL, Tools
A question that comes up on the forums all the time: Which query used the most CPU. You may see variations on, memory, I/O, or just resources in general. However, people want to know this information, and it's not readily apparent how to get it. While you can look at what's in cache through the DMVs to see the queries there, you don't get any real history and you don't get any detail of when the executions occurred. You can certainly take advantage of the Query Store for this kind of information. However, even that data is aggregated by hour. If you really want a detailed analysis of which query used the most CPU, you need to first set up an Extended Events session and then consume that data. A…
Read More

Learning Jupyter Notebooks

Azure, Professional Development, Tools
I'm starting the process of learning how to use Jupyter Notebooks. Notebooks are documents that contain live code, commentary, results, pictures and more. Jupyter Notebooks are used for presentations, documentation, run books, troubleshooting guides and lots more. Their support within Azure Data Studio opens up lots of opportunities. Azure Data Studio If you're interested in learning about notebooks yourself, or, as I publish the notebooks that I put together and you want to consume them, you need to have a mechanism. There are any number of third party or open source solutions to read notebooks. However, since I'm focused primarily on the Microsoft data platform, I'm using Azure Data Studio to do this work. I've written in the past about using Azure Data Studio (ADS). I also have a bunch…
Read More

Missing Indexes in the Query Store

SQL Server 2016, SQL Server 2017, T-SQL, Tools
I've shown before how to use the DMVs that read the plan cache as a way to connect the missing indexes suggestions with specific queries, but the other place to find missing index suggestions is the Query Store. Pulling from the Query Store The plans stored in the Query Store are exactly the same as the plans stored within the plan cache. This means that the XML is available and you can try to retrieve information from it directly, just as we did with the missing index queries against the DMVs. Here's the query modified for the Query Store: WITH XMLNAMESPACES (DEFAULT 'http://schemas.microsoft.com/sqlserver/2004/07/showplan') SELECT qsqt.query_sql_text, rts.plan_id, rts.NumExecutions, rts.MinDuration, rts.MaxDuration, rts.AvgDuration, rts.AvgReads, rts.AvgWrites, qsp.QueryPlan, qsp.QueryPlan.value(N'(//MissingIndex/@Table)[1]', 'NVARCHAR(256)') AS TableName, qsp.QueryPlan.value(N'(//MissingIndex/@Schema)[1]', 'NVARCHAR(256)') AS SchemaName, qsp.QueryPlan.value(N'(//MissingIndexGroup/@Impact)[1]', 'DECIMAL(6,4)') AS ProjectedImpact, ColumnGroup.value('./@Usage', 'NVARCHAR(256)') AS ColumnGroupUsage, ColumnGroupColumn.value('./@Name',…
Read More