@@ -9,6 +9,15 @@ const { parseProcedure } = require('../helpers/parsers/parseProcedure');
99
1010const PERMISSION_DENIED_CODE = 297 ;
1111
12+ const normalizeQueryForLogging = queryParams =>
13+ queryParams . map ( param => {
14+ if ( typeof param === 'string' ) {
15+ return param . replace ( / \t / g, ' ' ) ;
16+ }
17+
18+ return param ;
19+ } ) ;
20+
1221const addPermissionDeniedMetaData = ( { error, meta } ) => {
1322 error . message =
1423 'The user does not have permission to perform ' +
@@ -33,7 +42,12 @@ const getClient = async ({ client, dbName, meta, logger }) => {
3342 } ,
3443 async query ( ...queryParams ) {
3544 try {
36- return await currentDbConnectionClient . query ( ...queryParams ) ;
45+ logger . log ( 'info' , { query : normalizeQueryForLogging ( queryParams ) } , 'Performing query' ) ;
46+ const start = Date . now ( ) ;
47+ const result = await currentDbConnectionClient . query ( ...queryParams ) ;
48+ const duration = Date . now ( ) - start ;
49+ logger . log ( 'info' , { 'action' : meta . action , duration : `${ duration } ms` } , 'Query executed' ) ;
50+ return result ;
3751 } catch ( error ) {
3852 if ( meta ) {
3953 if ( error . number === PERMISSION_DENIED_CODE ) {
@@ -265,6 +279,7 @@ const getDatabaseIndexes = async ({ client, dbName, tablesInfo, logger }) => {
265279 } ) ;
266280
267281 logger . log ( 'info' , { message : `Get '${ dbName } ' database indexes.` } , 'Reverse Engineering' ) ;
282+ logger . progress ( { message : 'Discovering table index metadata' , containerName : dbName , entityName : '' } ) ;
268283
269284 const tableAlias = 't' ;
270285 const leftJoinClauseParts = Object . entries ( tablesInfo ) . map ( ( [ schemaName , tableNames ] ) => {
@@ -315,6 +330,8 @@ const getIndexesBucketCount = async ({ client, dbName, indexesId, logger }) => {
315330 logger,
316331 } ) ;
317332
333+ logger . log ( 'info' , { message : `Get '${ dbName } ' database indexes bucket count.` } , 'Reverse Engineering' ) ;
334+
318335 return mapResponse (
319336 await currentDbConnectionClient . query ( `
320337 SELECT hs.total_bucket_count, hs.index_id
@@ -343,6 +360,7 @@ const getSpatialIndexes = async ({ client, dbName, allUniqueSchemasAndTables, lo
343360 } ) ;
344361
345362 logger . log ( 'info' , { message : `Get '${ dbName } ' database spatial indexes.` } , 'Reverse Engineering' ) ;
363+ logger . progress ( { message : 'Discovering spatial index metadata' , containerName : dbName , entityName : '' } ) ;
346364
347365 const tableAlias = 't' ;
348366 const whereClauseParts = getWhereClauseForUniqueSchemasAndTables ( { tableAlias, allUniqueSchemasAndTables } ) ;
@@ -400,6 +418,7 @@ const getFullTextIndexes = async ({ client, dbName, allUniqueSchemasAndTables, l
400418 } ) ;
401419
402420 logger . log ( 'info' , { message : `Get '${ dbName } ' database full text indexes.` } , 'Reverse Engineering' ) ;
421+ logger . progress ( { message : 'Discovering full-text index metadata' , containerName : dbName , entityName : '' } ) ;
403422
404423 const tableAlias = 'F' ;
405424 const whereClauseParts = getWhereClauseForUniqueSchemasAndTables ( { tableAlias, allUniqueSchemasAndTables } ) ;
@@ -458,6 +477,7 @@ const getViewsIndexes = async ({ client, dbName, logger }) => {
458477 } ) ;
459478
460479 logger . log ( 'info' , { message : `Get '${ dbName } ' database views indexes.` } , 'Reverse Engineering' ) ;
480+ logger . progress ( { message : 'Discovering view index metadata' , containerName : dbName , entityName : '' } ) ;
461481
462482 const tableAlias = 'ind' ;
463483
@@ -536,21 +556,56 @@ const getDatabaseMemoryOptimizedTables = async ({ client, dbName, logger }) => {
536556 logger,
537557 } ) ;
538558
539- logger . log ( 'info' , { message : `Get '${ dbName } ' database memory optimized indexes.` } , 'Reverse Engineering' ) ;
559+ logger . log (
560+ 'info' ,
561+ { message : `Detecting if '${ dbName } ' database supports memory optimized tables.` } ,
562+ 'Reverse Engineering' ,
563+ ) ;
564+ logger . progress ( { message : 'Discovering memory-optimized table metadata' , containerName : dbName , entityName : '' } ) ;
565+
566+ const { isMemoryOptimizedTableSupported, isHistoryTableSupported } = await getSysTablesCatalogCapabilities ( {
567+ client,
568+ dbName,
569+ } ) ;
570+
571+ if ( ! isMemoryOptimizedTableSupported ) {
572+ logger . log (
573+ 'info' ,
574+ { message : `Memory optimized tables are not supported in '${ dbName } ' database.` } ,
575+ 'Reverse Engineering' ,
576+ ) ;
577+ return [ ] ;
578+ }
579+
580+ if ( isHistoryTableSupported ) {
581+ return mapResponse (
582+ await currentDbConnectionClient . query `
583+ SELECT
584+ T.name,
585+ T.durability,
586+ T.durability_desc,
587+ OBJECT_NAME(T.history_table_id) AS history_table,
588+ SCHEMA_NAME(O.schema_id) AS history_schema,
589+ T.temporal_type_desc,
590+ T.is_memory_optimized
591+ FROM sys.tables T
592+ LEFT JOIN sys.objects O
593+ ON T.history_table_id = O.object_id
594+ WHERE T.is_memory_optimized = 1
595+ ` ,
596+ ) ;
597+ }
598+
599+ logger . log ( 'info' , { message : `History tables are not supported in '${ dbName } ' database.` } , 'Reverse Engineering' ) ;
540600
541601 return mapResponse (
542602 await currentDbConnectionClient . query `
543603 SELECT
544604 T.name,
545605 T.durability,
546606 T.durability_desc,
547- OBJECT_NAME(T.history_table_id) AS history_table,
548- SCHEMA_NAME(O.schema_id) AS history_schema,
549- T.temporal_type_desc,
550607 T.is_memory_optimized
551608 FROM sys.tables T
552- LEFT JOIN sys.objects O
553- ON T.history_table_id = O.object_id
554609 WHERE T.is_memory_optimized = 1
555610 ` ,
556611 ) ;
@@ -569,6 +624,7 @@ const getDatabaseCheckConstraints = async ({ client, dbName, allUniqueSchemasAnd
569624 } ) ;
570625
571626 logger . log ( 'info' , { message : `Get '${ dbName } ' database check constraints.` } , 'Reverse Engineering' ) ;
627+ logger . progress ( { message : 'Discovering check constraint metadata' , containerName : dbName , entityName : '' } ) ;
572628
573629 const tableAlias = 't' ;
574630 const whereClauseParts = getWhereClauseForUniqueSchemasAndTables ( { tableAlias, allUniqueSchemasAndTables } ) ;
@@ -790,11 +846,10 @@ const getDatabaseXmlSchemaCollection = async ({ client, dbName, allUniqueSchemas
790846 } ) ;
791847
792848 logger . log ( 'info' , { message : `Get '${ dbName } ' database xml schema collection.` } , 'Reverse Engineering' ) ;
849+ logger . progress ( { message : 'Discovering XML schema collection metadata' , containerName : dbName , entityName : '' } ) ;
793850
794- const schemaAlias = 'xsc' ;
795851 const tableAlias = 'xcu' ;
796852 const whereClauseParts = getWhereClauseForUniqueSchemasAndTables ( {
797- schemaAlias,
798853 tableAlias,
799854 allUniqueSchemasAndTables,
800855 } ) ;
@@ -860,6 +915,7 @@ const getDatabaseUserDefinedTypes = async ({ client, dbName, logger }) => {
860915 } ) ;
861916
862917 logger . log ( 'info' , { message : `Get '${ dbName } ' database UDTs.` } , 'Reverse Engineering' ) ;
918+ logger . progress ( { message : 'Discovering user-defined type metadata' , containerName : dbName , entityName : '' } ) ;
863919
864920 return mapResponse ( currentDbConnectionClient . query `
865921 SELECT * FROM sys.types
@@ -889,6 +945,24 @@ const mapResponse = async (response = Promise.resolve({})) => {
889945 return resp . recordset ? resp . recordset : resp ;
890946} ;
891947
948+ const getSysTablesCatalogCapabilities = async ( { client, dbName } ) => {
949+ const connectionClient = await getNewConnectionClientByDb ( client , dbName ) ;
950+ const [ { Has_HistoryTableId, Has_IsMemoryOptimized } = { } ] = await mapResponse (
951+ connectionClient . query ( `
952+ SELECT
953+ COUNT(CASE WHEN name = 'history_table_id' THEN 1 END) AS Has_HistoryTableId,
954+ COUNT(CASE WHEN name = 'is_memory_optimized' THEN 1 END) AS Has_IsMemoryOptimized
955+ FROM sys.all_columns
956+ WHERE object_id = OBJECT_ID('sys.tables')
957+ ` ) ,
958+ ) ;
959+
960+ return {
961+ isHistoryTableSupported : Boolean ( Has_HistoryTableId ) ,
962+ isMemoryOptimizedTableSupported : Boolean ( Has_IsMemoryOptimized ) ,
963+ } ;
964+ } ;
965+
892966const getDescriptionComments = async ( { client, dbName, schema, entity, logger } ) => {
893967 const currentDbConnectionClient = await getClient ( {
894968 client,
@@ -922,12 +996,8 @@ const buildDescriptionCommentsRetrieveQuery = ({ schema, entity }) => {
922996 return `SELECT objtype, objname, value FROM fn_listextendedproperty ('MS_Description', ${ schemaTemplate } , ${ entityTemplate } );` ;
923997} ;
924998
925- const getWhereClauseForUniqueSchemasAndTables = ( {
926- schemaAlias,
927- tableAlias,
928- allUniqueSchemasAndTables : { schemas, tables } ,
929- } ) =>
930- `OBJECT_SCHEMA_NAME(${ schemaAlias || tableAlias } .object_id) IN (${ [ ...schemas ] . join ( ', ' ) } )
999+ const getWhereClauseForUniqueSchemasAndTables = ( { tableAlias, allUniqueSchemasAndTables : { schemas, tables } } ) =>
1000+ `OBJECT_SCHEMA_NAME(${ tableAlias } .object_id) IN (${ [ ...schemas ] . join ( ', ' ) } )
9311001 AND OBJECT_NAME(${ tableAlias } .object_id) IN (${ [ ...tables ] . join ( ', ' ) } )` ;
9321002
9331003const getDatabaseProcedures = async ( { client, dbName, logger } ) => {
@@ -943,6 +1013,7 @@ const getDatabaseProcedures = async ({ client, dbName, logger }) => {
9431013 } ) ;
9441014
9451015 logger . log ( 'info' , { message : `Get '${ dbName } ' database procedures.` } , 'Reverse Engineering' ) ;
1016+ logger . progress ( { message : 'Discovering stored procedure metadata' , containerName : dbName , entityName : '' } ) ;
9461017
9471018 const response = await currentDbConnectionClient . query ( `
9481019 SELECT
@@ -951,11 +1022,11 @@ const getDatabaseProcedures = async ({ client, dbName, logger }) => {
9511022 sm.definition AS procedure_body,
9521023 ep.value AS description
9531024 FROM sys.procedures p
954- JOIN sys.schemas s
1025+ JOIN sys.schemas s
9551026 ON p.schema_id = s.schema_id
956- LEFT JOIN sys.sql_modules sm
1027+ LEFT JOIN sys.sql_modules sm
9571028 ON p.object_id = sm.object_id
958- LEFT JOIN sys.extended_properties ep
1029+ LEFT JOIN sys.extended_properties ep
9591030 ON ep.major_id = p.object_id
9601031 AND ep.minor_id = 0
9611032 AND ep.name = 'MS_Description'
0 commit comments