95
Using Database Statistics to Make Capacity Planning Decisions Geoff Mower Senior Software Performance Engineer, Blackboard Steve Feldman Senior Director Software Performance Engineering and Architecture, Blackboard

Bb world 2011 capacity planning

Embed Size (px)

Citation preview

Page 1: Bb world 2011 capacity planning

Using Database Statistics to Make Capacity Planning

DecisionsGeoff Mower

Senior Software Performance Engineer, Blackboard

Steve FeldmanSenior Director Software Performance Engineering and Architecture, Blackboard

Page 2: Bb world 2011 capacity planning

Who Are We?Geoff Mower- Senior Software Performance Engineer

5 years on the frontlines as a DBA

Performance and Scalability for Outcomes & Community

2 hour interview on a plane

Page 3: Bb world 2011 capacity planning

Who Are We?Steve Feldman

• Blackboard since 2003• Performance Engineering

from the start• Platform Architecture in

2005• Security Engineering in

2010

“Love my job…love my team. If you email me, I will respond.”

@seven_seconds

http://goo.gl/Z4Rq5

Page 4: Bb world 2011 capacity planning

What We Want You to Do?

Mine your data Ask follow-up questionsask questions about your

data

Page 5: Bb world 2011 capacity planning

What are our obstacles?

• Certain data points are transient– Logging will need to be created in certain situations

to fill in missing data points.• See slide #45 & #46 for an example

Page 6: Bb world 2011 capacity planning

What You Need

• Permissions to run SQL scripts on your Blackboard Learn environment's database

• Basic SQL fundamentals• Analysis of results• Database Tools

– Aquadata client & Server or Quest’s Toad

Page 7: Bb world 2011 capacity planning

Skill and Knowledge SetsOpen DB Documentation

• Blackboard Learn™, Release 9.1 Open Database Document– http://bit.ly/loW9hi

Page 8: Bb world 2011 capacity planning
Page 9: Bb world 2011 capacity planning

Asking the Right Questions

Organizing and Analyzing the Data

Ask Follow-up Questions

Making Decisions

Collecting the Right Data

Page 10: Bb world 2011 capacity planning

Types of Data

Data Types Table ExampleEvent ACTIVITY_ACCUMULATOR User navigation

Process COURSE_USERS snapshot

User COURSE_CONTENT User created entities

Static LEARN_admin.bb_instance installation

Transient SESSIONS Tracks who has an active session

Page 11: Bb world 2011 capacity planning

Areas of Capacity Planning

• How can the Blackboard Learn schema help you capacity plan for your business requirements in regards to?

Strategic Functional Decisions

Expense and Budget Management

Administrative Planning

Page 12: Bb world 2011 capacity planning

Administrative Planning

Page 13: Bb world 2011 capacity planning

Administrative Planning

To be able to restore individual courses, can we use the course archive tool as a backup function?

Page 14: Bb world 2011 capacity planning

Administrative PlanningAsking the Right Questions

How will we know which courses need archiving?

Frequency of course archive task?

Will the archiving process impact user experience?

Does the course archive tool have limitation?

Location of course archives?

Page 15: Bb world 2011 capacity planning

Administrative PlanningCollecting the Right Data

How will we know which courses need archiving?– Course entity creation and modification

Creation TablesCOURSE_CONTENTSGRADEBOOK_MAIN

GRADEBOOK_GRADESQTI_ASI_DATA

QTI_RESULT_DATAFORUM_MAIN

MSG_MAIN

Modification TablesCOURSE_CONTENTSGRADEBOOK_MAIN

GRADEBOOK_GRADESQTI_ASI_DATA

QTI_RESULT_DATAFORUM_MAIN

MSG_MAINCALENDAR

STAFFINFORMATION

Page 16: Bb world 2011 capacity planning

Administrative PlanningOrganizing and Analyzing the Data

• Data Points: Course/Organizations to be archived SQL/Oracle

COURSE_ID Number of New/Modified Course Entities

Hist_101 42

Eng_252 42

Sci_139 38

Eng_429 37

Art_202 35

Eco_323 35

Page 17: Bb world 2011 capacity planning

Administrative PlanningMaking Decisions from the Data

• How many new or modified course/organization entities are required for a course/organization to be archived?

• How many courses/organizations should we archive each time the archive task is execution?

• What is the maximum time between archive tasks?

Page 18: Bb world 2011 capacity planning

Administrative PlanningActing on Your Descion

SQL/OracleHist_101, c:\Course_Archives\2011-07-09\Eng_252, c:\Course_Archives\2011-07-09\Sci_139, c:\Course_Archives\2011-07-09\Eng_429, c:\Course_Archives\2011-07-09\…• Create a JOB that would run the SQL script to generate a txt

file containing the query results

• Create a schedule task that would run the batch_ImportExport.bat tool and direct it to the txt file created by the JOB in the previous step.

Page 19: Bb world 2011 capacity planning

Expense and Budget Management

Page 20: Bb world 2011 capacity planning

Asking the Right QuestionsExpense and Budget Management

• How much do we need to budget for in order to fund our database requirements?

Page 21: Bb world 2011 capacity planning

Expense and Budget Management

• When are we going to hit our 95% disk spaced used threshold.

Page 22: Bb world 2011 capacity planning

Expense and Budget Management

• Available disk space issue– Talk to Network Security Manager (owner of the SAN)

• We need more disk space

Page 23: Bb world 2011 capacity planning

Expense and Budget ManagementAsking the Right Questions

• What did I miss?– When will we run out of space?– How long do we expect the requested disk space to

last us?

• Facts vs. guess work

Page 24: Bb world 2011 capacity planning

Expense and Budget ManagementCollecting the Right Data

• Data Points: Database file size• Binary• Data Files (.mdf)• TempDB• Transaction Logs (.ldf)• Back-up/restore process

Page 25: Bb world 2011 capacity planning

Expense and Budget ManagementOrganizing and Analyzing the Data

• Data Points: Database file size SQL/Oracle

Database Name Physical Name Size in MB

BBLEARN_stats F:\data\BBLEARN_stats_data.mdf 70338

BBLEARN F:\data\BBLEARN_data.mdf 45520

cms_files_inst F:\data\cms_files_inst_data.mdf 5704

BBLEARN G:\logs\BBLEARN_log.ldf 3083

cms_files_inst G:\logs\cms_files_inst_log.ldf 1361

cms_files_courses F:\data\cms_files_courses_data.mdf 1072

cms_files_users F:\data\cms_files_users_data.mdf 926

msdb F:\data\MSSQL.1\MSSQL\DATA\MSDBData.mdf 792

cms_files_library F:\data\cms_files_library_data.mdf 720

cms_files_orgs F:\data\cms_files_orgs_data.mdf 384

msdb F:\data\MSSQL.1\MSSQL\DATA\MSDBLog.ldf 259

cms_files_users G:\logs\cms_files_users_log.ldf 214

cms_files_courses G:\logs\cms_files_courses_log.ldf 207

Page 26: Bb world 2011 capacity planning

Expense and Budget ManagementOrganizing and Analyzing the Data

• Data Points: Table Row Count and Sizes SQL/Oracle

Table NameRow

Count Reserved Data Index Size Unused

ACTIVITY_ACCUMULATOR 377266616 84097056 46905888 37183888 7280

COURSE_USERS 3837931 496024 258272 237496 256

USERS 303687 139480 96848 42440 192

COURSE_MAIN 121623 86024 47760 37984 280

NAVIGATION_ITEM 1876 2032 608 1128 296

SYSTEM_TRACKING 3550 1936 1672 160 104

USER_ROLES 4114 544 160 288 96

Page 27: Bb world 2011 capacity planning

Expense and Budget ManagementOrganizing and Analyzing the Data

Data Points: Table growth rate (by year) of the Activity_Accumulator SQL/Oracle

2003 2004 2005 2006 2007 2008 2009 20100

20000000

40000000

60000000

80000000

100000000

120000000

Page 28: Bb world 2011 capacity planning

Expense and Budget Management

• Data Points: Table growth rate (by year) of the COURSE_USERS table

2003 2004 2005 2006 2007 2008 2009 20100

200000

400000

600000

800000

1000000

1200000

1400000

Page 29: Bb world 2011 capacity planning

Expense and Budget ManagementOrganizing and Analyzing the Data

Data Points: ACTIVITY_ACCUMULATOR growth rate (by month) SQL/Oracle

January

Febru

aryMarc

hApril

MayJune

July

August

Septem

ber

October

November

December

0

2000000

4000000

6000000

8000000

10000000

12000000

Page 30: Bb world 2011 capacity planning

Expense and Budget Management

• Data Points: COURSE_USERS table growth rate (by month)

August August August0

100000

200000

300000

400000

500000

600000

700000

800000

900000

Page 31: Bb world 2011 capacity planning

Expense and Budget ManagementMaking Decisions from the Data

• Conclusion• Due to opening of school tasks we will see our

available disk space decrease below 5% during the month of August.

• In order to make it 3 years we will need a minimum 120 GB.

Page 32: Bb world 2011 capacity planning

Strategic Functional Decisions

Page 33: Bb world 2011 capacity planning

Strategic Functional Decisions

• Can our database support all classroom testing if it was online?

Page 34: Bb world 2011 capacity planning

Strategic Functional DecisionsAsking the Right Questions

•Study…• Online & offline test taking populations• The tests themselves• Test taking behavior • How testing impacts the database• Locating when you will see resource contention

Page 35: Bb world 2011 capacity planning

Strategic Functional DecisionsHistorical Use of Online Testing

What is the percent of students from the previous term that have completed a test online? SQL/Oracle

OnlineOffline

Page 36: Bb world 2011 capacity planning

Strategic Functional DecisionsHistorical Use of Online Testing

How many tests have been completed per enrollment? SQL/Oracle

1 2 3 4 5 6 7 8 9 100

100

200

300

400

500

600

700

800

900

1000

Page 37: Bb world 2011 capacity planning

Strategic Functional DecisionsHistorical Use of Online Testing

Test question submission by hour of the day? SQL/Oracle

Test question Submission by day of the week? SQL/Oracle

12:00:00 AM

01:00:00 AM

02:00:00 AM

03:00:00 AM

04:00:00 AM

05:00:00 AM

06:00:00 AM

07:00:00 AM

08:00:00 AM

09:00:00 AM

10:00:00 AM

11:00:00 AM

12:00:00 PM

01:00:00 PM

02:00:00 PM

03:00:00 PM

04:00:00 PM

05:00:00 PM

06:00:00 PM

07:00:00 PM

08:00:00 PM

09:00:00 PM

10:00:00 PM

11:00:00 PM

0

20000

40000

60000

80000

Sunday Monday Tuesday Wednesday Thursday Friday Saturday0

20000

40000

60000

80000

100000

120000

Page 38: Bb world 2011 capacity planning

Strategic Functional DecisionsHistorical Use of Online Testing

How many test questions were submitted per hour? SQL/Oracle

1 2 3 4 5 6 7 8 90

10000

20000

30000

40000

50000

60000

70000

Page 39: Bb world 2011 capacity planning

Strategic Functional DecisionsCollecting the Right Data

Previous Use Full Adoption

Courses with Tests 11,274 55,504

Enrollments with Tests 225,480 1,110,080

Number of questions submitted in a term

4,219,032 25,694,266

Peak Question Submission by hour

60,346 297,094

Page 40: Bb world 2011 capacity planning

Strategic Functional DecisionsCollecting the Right Data

• Determine CPU and I/O cost of testing (SQL server)– Track the Stored Procedures performing the works SQL/

Oracle» qti_result_data_cr» update_gradebook_grade» attempt_cr» update_qti_res_bbmd_dtmod» gb2_is_log_enabled» gb2_attempt_logger

Page 41: Bb world 2011 capacity planning

Strategic Functional DecisionsOrganizing and Analyzing the Data

• Determine CPU and I/O cost of testing (SQL server)– Track the Stored Procedures performing the works SQL/Oracle

Page 42: Bb world 2011 capacity planning

Strategic Functional DecisionsOrganizing and Analyzing the Data

• Determine CPU and I/O cost of testing– Track the queries performing the work SQL/Oracle

Page 43: Bb world 2011 capacity planning

Strategic Functional DecisionsOrganizing and Analyzing the Data

Determine IO cost of all cached stored procedures SQL/Oracle

get_d

efault_

module_lay

outs

gb2_a

ttempt_l

ogger

attem

pt_cr

sessio

ns_batc

h_rm

update_g

radeb

ook_gra

de

sessio

ns_cr

update_q

ti_res_b

bmd_dtm

od

activit

y_acc

umulator_u

pdate

gb2_is

_log_

enab

led

qti_resu

lt_data

_cr0

100

200

300

400

500

600

700

Average IO

Page 44: Bb world 2011 capacity planning

Strategic Functional DecisionsMaking Decisions from the Data

•A reasonable understanding…• How tests are currently used• How tests will be used• How much each question costs the database upon

submission

•Lack information on…• Baseline of database’s IO and CPU resources• Non-testing database transactions

Page 45: Bb world 2011 capacity planning

Strategic Functional DecisionsCollecting the Right Data

• Determine the breaking point of CPU and I/O of testing– Create a CPU logging script SQL/Oracle

• SQL server logging limitation– 4 hours of CPU tracking– Lacks IO counters

– Create a IO logging script SQL/Oracle• Snapshot in time

– Need to log the delta between the last logged IO metric and current query results

– Create a Query logging script SQL/Oracle• Compares test question submission to all other transactions

Page 46: Bb world 2011 capacity planning

Strategic Functional DecisionsCollecting the Right Data

• Create a separate database from the Blackboard Learn’s databases (you can use the database server Blackboard Learn is running on)

• Create tables with in the new database that match the query results you wish to store

• Create a JOB that will run each query and insert the results into the corresponding table and database.

Page 47: Bb world 2011 capacity planning

Capacity Planning is an art if done

properly…

or a disaster if not done at all.

Page 48: Bb world 2011 capacity planning

[email protected]

@gvmower

Page 49: Bb world 2011 capacity planning

@seven_seconds

sevenseconds.wordpress.com

[email protected]

http://goo.gl/Z4Rq5

Page 50: Bb world 2011 capacity planning

Please provide feedback for this session by [email protected].

The title of this session is:

Using Database Statistics to Make Capacity Planning Decisions

Page 51: Bb world 2011 capacity planning

Appendices

Page 52: Bb world 2011 capacity planning

Administrative PlanningWhat courses meet the course archive criteria

declare @Last_Archive datetimedeclare @Datediff intdeclare @Number_of_New_Entities int

set @Last_Archive = '2011-6-7' --Enter the last datetime the course archival process ranset @Datediff = 24 --Enter the time duration between course creation and course entities you would like to track. For example, to avoid archive courses that were created since the last archive process enter the time of your longest running snapshot or SIS process in terms of hours.set @Number_of_New_Entities = 1 --Enter the number of new course entities required for a course to be archived

select course_id, CC.CC + GM.GM + GG.GG + QA.QA + A.A + ConM.CONFERENCE_MAIN + FM.FORUM_MAIN + MM.MSG_MAIN + C.C + S.S AS [Number of New/Modified Course Entities]from course_main cmleft join (select crsmain_pk1, COUNT(cc.pk1) CC

from course_contents ccleft join course_main cm on cm.pk1 = cc.crsmain_pk1where (cc.dtcreated > @Last_Archiveor cc.dtmodified > @Last_Archive)and datediff(hour, cm.dtcreated, cc.dtcreated) > @Datediffgroup by crsmain_pk1) CC on CC.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(gm.pk1) GMfrom gradebook_main gmleft join course_main cm on cm.pk1 = gm.crsmain_pk1where (date_added > @Last_Archiveor date_modified > @Last_Archive)and datediff(hour, cm.dtcreated, gm.date_added) > @Datediffgroup by crsmain_pk1) GM on GM.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(gg.pk1) GGfrom gradebook_main gmleft join gradebook_grade gg on gm.pk1 = gg.gradebook_main_pk1left join course_main cm on gm.crsmain_pk1 = cm.pk1where (gg.date_added > @Last_ArchiveOR gg.date_modified > @Last_Archive)and datediff(hour, cm.dtcreated, gg.date_added) > @Datediffgroup by crsmain_pk1) GG on GG.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(qa.pk1) QAfrom qti_asi_data qaleft join course_main cm on cm.pk1 = qa.crsmain_pk1where (bbmd_date_added > @Last_ArchiveOR bbmd_date_modified > @Last_Archive)and datediff(hour, cm.dtcreated, qa.bbmd_date_added) > @Datediffgroup by crsmain_pk1) QA on QA.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(a.pk1) Afrom attempt aleft join gradebook_grade gg on a.pk1 = gg.last_attempt_pk1left join gradebook_main gm on gm.pk1 = gg.gradebook_main_pk1left join course_main cm on cm.pk1 = gm.crsmain_pk1where (a.attempt_date > @Last_Archiveor a.date_modified > @Last_Archive)and datediff(hour, cm.dtcreated, a.attempt_date) > @Datediffgroup by crsmain_pk1) A on A.crsmain_pk1 = cm.pk1

left join (select co.owner_pk1, COUNT(CON.pk1) CONFERENCE_MAINfrom conference_owner COleft join conference_main CON on CON.conference_owner_pk1 = CO.pk1left join course_main cm on cm.pk1 = co.owner_pk1where co.owner_table = 'COURSE_MAIN'and (CON.dtcreated > @Last_ArchiveOR CON.dtmodified > @Last_Archive)and datediff(hour, cm.dtcreated, con.dtcreated) > @Datediffgroup by owner_pk1) ConM on ConM.OWNER_PK1 = cm.pk1

left join (select co.owner_pk1, COUNT(fr.pk1) FORUM_MAINfrom conference_owner COleft join conference_main CON on CON.conference_owner_pk1 = CO.pk1left join forum_main fr on fr.confmain_pk1 = CON.pk1left join course_main cm on cm.pk1 = co.owner_pk1where owner_table = 'COURSE_MAIN'and (fr.dtcreated > @Last_ArchiveOR fr.dtmodified > @Last_Archive)and datediff(hour, cm.dtcreated, fr.dtcreated) > @Datediffgroup by owner_pk1) FM on FM.OWNER_PK1 = cm.pk1

left join (select co.owner_pk1, COUNT(mm.pk1) MSG_MAINfrom conference_owner COleft join conference_main CON on CON.conference_owner_pk1 = CO.pk1left join forum_main fr on fr.confmain_pk1 = CON.pk1left join msg_main mm on mm.forummain_pk1 = fr.pk1left join msg_main mm_reply on mm_reply.msgmain_pk1 = mm.pk1left join course_main cm on cm.pk1 = co.owner_pk1where owner_table = 'COURSE_MAIN'and (mm.dtcreated > @Last_ArchiveOR mm.dtmodified > @Last_Archive)and datediff(hour, cm.dtcreated, mm.dtcreated) > @Datediffgroup by owner_pk1) MM on MM.OWNER_PK1 = cm.pk1

left join (select crsmain_pk1, COUNT(c.pk1) Cfrom calendar cleft join course_main cm on cm.pk1 = c.crsmain_pk1where c.dtmodified > @Last_Archiveand datediff(hour, cm.dtcreated, c.dtmodified) > @Datediffgroup by crsmain_pk1) C on C.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(s.pk1) Sfrom staffinformation Sleft join course_main cm on cm.pk1 = s.crsmain_pk1where s.dtmodified > @Last_Archiveand datediff(hour, cm.dtcreated, s.dtmodified) > @Datediffgroup by crsmain_pk1) S on S.crsmain_pk1 = cm.pk1

Page 53: Bb world 2011 capacity planning

Administrative PlanningWhat courses meet the course archive criteria

set serveroutput on size 100000

---Administrative PlanningWhat courses meet the course archive criteria

declare

v_Last_Archive date;

v_Datediff int;

v_Number_of_New_Entities int;

v_Directory varchar(256);

v_File_Name varchar(256);

Begin

v_Last_Archive := TO_DATE('7-JUN-2011'); --Enter the last datetime the course archival process ran

v_Datediff := 1 ; --this is the day

--Enter the time duration between course creation and course entities you would like to track. For example, to avoid archive courses that were created ----since the last archive process enter the time of your longest running snapshot or SIS process in terms of hours.

v_Number_of_New_Entities := 1;

--Enter the number of new course entities required for a course to be archived

select 'usr\local\blackboard\Course_Archives\' || TO_CHAR(SYSDATE, 'DD-Mon-YYYY') || '\' into v_Directory FROM Dual;

--Alter the string to build the directory you wish to store your archives

dbms_output.enable(9999999);

dbms_output.new_line();

FOR rec IN (

select course_id || v_Directory as output

from course_main cm

left join (select crsmain_pk1, COUNT(cc.pk1) CC

from course_contents cc

left join course_main cm on cm.pk1 = cc.crsmain_pk1

where (cc.dtcreated > v_Last_Archive

or cc.dtmodified > v_Last_Archive)

and cm.dtcreated- cc.dtcreated> v_Datediff

group by crsmain_pk1) CC on CC.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(gm.pk1) GM

from gradebook_main gm

left join course_main cm on cm.pk1 = gm.crsmain_pk1

where (date_added > v_Last_Archive

or date_modified > v_Last_Archive)

and cm.dtcreated- gm.date_added> v_Datediff

group by crsmain_pk1) GM on GM.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(gg.pk1) GG

from gradebook_main gm

left join gradebook_grade gg on gm.pk1 = gg.gradebook_main_pk1

left join course_main cm on gm.crsmain_pk1 = cm.pk1

where (gg.date_added > v_Last_Archive

OR gg.date_modified > v_Last_Archive)

and cm.dtcreated- gg.date_added> v_Datediff

group by crsmain_pk1) GG on GG.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(qa.pk1) QA

from qti_asi_data qa

left join course_main cm on cm.pk1 = qa.crsmain_pk1

where (bbmd_date_added > v_Last_Archive

OR bbmd_date_modified > v_Last_Archive)

and cm.dtcreated- qa.bbmd_date_added> v_Datediff

group by crsmain_pk1) QA on QA.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(a.pk1) A

from attempt a

left join gradebook_grade gg on a.pk1 = gg.last_attempt_pk1

left join gradebook_main gm on gm.pk1 = gg.gradebook_main_pk1

left join course_main cm on cm.pk1 = gm.crsmain_pk1

where (a.attempt_date > v_Last_Archive

or a.date_modified > v_Last_Archive)

and cm.dtcreated- a.attempt_date > v_Datediff

group by crsmain_pk1) A on A.crsmain_pk1 = cm.pk1

left join (select co.owner_pk1, COUNT(CON.pk1) CONFERENCE_MAIN

from conference_owner CO

left join conference_main CON on CON.conference_owner_pk1 = CO.pk1

left join course_main cm on cm.pk1 = co.owner_pk1

where co.owner_table = 'COURSE_MAIN'

and (CON.dtcreated > v_Last_Archive

OR CON.dtmodified > v_Last_Archive)

and cm.dtcreated-con.dtcreated > v_Datediff

group by owner_pk1) ConM on ConM.OWNER_PK1 = cm.pk1

left join (select co.owner_pk1, COUNT(fr.pk1) FORUM_MAIN

from conference_owner CO

left join conference_main CON on CON.conference_owner_pk1 = CO.pk1

left join forum_main fr on fr.confmain_pk1 = CON.pk1

left join course_main cm on cm.pk1 = co.owner_pk1

where owner_table = 'COURSE_MAIN'

and (fr.dtcreated > v_Last_Archive

OR fr.dtmodified > v_Last_Archive)

and cm.dtcreated- fr.dtcreated > v_Datediff

group by owner_pk1) FM on FM.OWNER_PK1 = cm.pk1

left join (select co.owner_pk1, COUNT(mm.pk1) MSG_MAIN

from conference_owner CO

left join conference_main CON on CON.conference_owner_pk1 = CO.pk1

left join forum_main fr on fr.confmain_pk1 = CON.pk1

left join msg_main mm on mm.forummain_pk1 = fr.pk1

left join msg_main mm_reply on mm_reply.msgmain_pk1 = mm.pk1

left join course_main cm on cm.pk1 = co.owner_pk1

where owner_table = 'COURSE_MAIN'

and (mm.dtcreated > v_Last_Archive

OR mm.dtmodified > v_Last_Archive)

and cm.dtcreated- mm.dtcreated > v_Datediff

group by owner_pk1) MM on MM.OWNER_PK1 = cm.pk1

left join (select crsmain_pk1, COUNT(c.pk1) C

from calendar c

left join course_main cm on cm.pk1 = c.crsmain_pk1

where c.dtmodified > v_Last_Archive

and cm.dtcreated- c.dtmodified > v_Datediff

group by crsmain_pk1) C on C.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(s.pk1) S

from staffinformation S

left join course_main cm on cm.pk1 = s.crsmain_pk1

where s.dtmodified > v_Last_Archive

and cm.dtcreated- s.dtmodified > v_Datediff

group by crsmain_pk1) S on S.crsmain_pk1 = cm.pk1

where nvl(CC.CC,0) + nvl(GM.GM,0) + nvl(GG.GG,0) + nvl(QA.QA,0) + nvl(A.A,0) + nvl(ConM.CONFERENCE_MAIN,0) + nvl(FM.FORUM_MAIN,0) + nvl(MM.MSG_MAIN,0) + nvl(S.S,0) + nvl(C.C,0) >= v_Number_of_New_Entities)

LOOP

dbms_output.put_line (rec.output);

END LOOP;

dbms_output.new_line();

end;

Page 54: Bb world 2011 capacity planning

Administrative PlanningWhat courses meet the course archive criteria

declare @Last_Archive datetimedeclare @Datediff intdeclare @Number_of_New_Entities intdeclare @Directory varchar(256)declare @File_Name varchar(256)

set @Last_Archive = '2011-6-7' --Enter the last datetime the course archival process ranset @Datediff = 24 --Enter the time duration between course creation and course entities you would like to track. For example, to avoid archive courses that were created since the last archive process enter the time of your longest running snapshot or SIS process in terms of hours.set @Number_of_New_Entities = 1 --Enter the number of new course entities required for a course to be archivedset @Directory = (SELECT ', c:\Course_Archives\' + CAST(CONVERT(date, GETDATE()) as varchar(10)) + '\') --Alter the string to build the directory you wish to store your archives

select course_id + @Directoryfrom course_main cmleft join (select crsmain_pk1, COUNT(cc.pk1) CC

from course_contents ccleft join course_main cm on cm.pk1 = cc.crsmain_pk1where (cc.dtcreated > @Last_Archiveor cc.dtmodified > @Last_Archive)and datediff(hour, cm.dtcreated, cc.dtcreated) > @Datediffgroup by crsmain_pk1) CC on CC.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(gm.pk1) GMfrom gradebook_main gmleft join course_main cm on cm.pk1 = gm.crsmain_pk1where (date_added > @Last_Archiveor date_modified > @Last_Archive)and datediff(hour, cm.dtcreated, gm.date_added) > @Datediffgroup by crsmain_pk1) GM on GM.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(gg.pk1) GGfrom gradebook_main gmleft join gradebook_grade gg on gm.pk1 = gg.gradebook_main_pk1left join course_main cm on gm.crsmain_pk1 = cm.pk1where (gg.date_added > @Last_ArchiveOR gg.date_modified > @Last_Archive)and datediff(hour, cm.dtcreated, gg.date_added) > @Datediffgroup by crsmain_pk1) GG on GG.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(qa.pk1) QAfrom qti_asi_data qaleft join course_main cm on cm.pk1 = qa.crsmain_pk1where (bbmd_date_added > @Last_ArchiveOR bbmd_date_modified > @Last_Archive)and datediff(hour, cm.dtcreated, qa.bbmd_date_added) > @Datediffgroup by crsmain_pk1) QA on QA.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(a.pk1) Afrom attempt aleft join gradebook_grade gg on a.pk1 = gg.last_attempt_pk1left join gradebook_main gm on gm.pk1 = gg.gradebook_main_pk1left join course_main cm on cm.pk1 = gm.crsmain_pk1where (a.attempt_date > @Last_Archiveor a.date_modified > @Last_Archive)and datediff(hour, cm.dtcreated, a.attempt_date) > @Datediffgroup by crsmain_pk1) A on A.crsmain_pk1 = cm.pk1

left join (select co.owner_pk1, COUNT(CON.pk1) CONFERENCE_MAINfrom conference_owner COleft join conference_main CON on CON.conference_owner_pk1 = CO.pk1left join course_main cm on cm.pk1 = co.owner_pk1where co.owner_table = 'COURSE_MAIN'and (CON.dtcreated > @Last_ArchiveOR CON.dtmodified > @Last_Archive)and datediff(hour, cm.dtcreated, con.dtcreated) > @Datediffgroup by owner_pk1) ConM on ConM.OWNER_PK1 = cm.pk1

left join (select co.owner_pk1, COUNT(fr.pk1) FORUM_MAINfrom conference_owner COleft join conference_main CON on CON.conference_owner_pk1 = CO.pk1left join forum_main fr on fr.confmain_pk1 = CON.pk1left join course_main cm on cm.pk1 = co.owner_pk1where owner_table = 'COURSE_MAIN'and (fr.dtcreated > @Last_ArchiveOR fr.dtmodified > @Last_Archive)and datediff(hour, cm.dtcreated, fr.dtcreated) > @Datediffgroup by owner_pk1) FM on FM.OWNER_PK1 = cm.pk1

left join (select co.owner_pk1, COUNT(mm.pk1) MSG_MAINfrom conference_owner COleft join conference_main CON on CON.conference_owner_pk1 = CO.pk1left join forum_main fr on fr.confmain_pk1 = CON.pk1left join msg_main mm on mm.forummain_pk1 = fr.pk1left join msg_main mm_reply on mm_reply.msgmain_pk1 = mm.pk1left join course_main cm on cm.pk1 = co.owner_pk1where owner_table = 'COURSE_MAIN'and (mm.dtcreated > @Last_ArchiveOR mm.dtmodified > @Last_Archive)and datediff(hour, cm.dtcreated, mm.dtcreated) > @Datediffgroup by owner_pk1) MM on MM.OWNER_PK1 = cm.pk1

left join (select crsmain_pk1, COUNT(c.pk1) Cfrom calendar cleft join course_main cm on cm.pk1 = c.crsmain_pk1where c.dtmodified > @Last_Archiveand datediff(hour, cm.dtcreated, c.dtmodified) > @Datediffgroup by crsmain_pk1) C on C.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(s.pk1) Sfrom staffinformation Sleft join course_main cm on cm.pk1 = s.crsmain_pk1where s.dtmodified > @Last_Archiveand datediff(hour, cm.dtcreated, s.dtmodified) > @Datediffgroup by crsmain_pk1) S on S.crsmain_pk1 = cm.pk1

where ISNULL(CC.CC,0) + ISNULL(GM.GM,0) + ISNULL(GG.GG,0) + ISNULL(QA.QA,0) + ISNULL(A.A,0) + ISNULL(ConM.CONFERENCE_MAIN,0) + ISNULL(FM.FORUM_MAIN,0) + ISNULL(MM.MSG_MAIN,0) + ISNULL(S.S,0) + ISNULL(C.C,0) >= @Number_of_New_Entities

Page 55: Bb world 2011 capacity planning

Administrative PlanningWhat courses meet the course archive criteria

set serveroutput on size 100000

---Administrative PlanningWhat courses meet the course archive criteria

declare

v_Last_Archive date;

v_Datediff int;

v_Number_of_New_Entities int;

v_Directory varchar(256);

v_File_Name varchar(256);

Begin

v_Last_Archive := TO_DATE('7-JUN-2011'); --Enter the last datetime the course archival process ran

v_Datediff := 1 ; --this is the day

--Enter the time duration between course creation and course entities you would like to track. For example, to avoid archive courses that were created ----since the last archive process enter the time of your longest running snapshot or SIS process in terms of hours.

v_Number_of_New_Entities := 1;

--Enter the number of new course entities required for a course to be archived

select 'usr\local\blackboard\Course_Archives\' || TO_CHAR(SYSDATE, 'DD-Mon-YYYY') || '\' into v_Directory FROM Dual;

--Alter the string to build the directory you wish to store your archives

dbms_output.enable(9999999);

dbms_output.new_line();

FOR rec IN (

select course_id || v_Directory as output

from course_main cm

left join (select crsmain_pk1, COUNT(cc.pk1) CC

from course_contents cc

left join course_main cm on cm.pk1 = cc.crsmain_pk1

where (cc.dtcreated > v_Last_Archive

or cc.dtmodified > v_Last_Archive)

and cm.dtcreated- cc.dtcreated> v_Datediff

group by crsmain_pk1) CC on CC.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(gm.pk1) GM

from gradebook_main gm

left join course_main cm on cm.pk1 = gm.crsmain_pk1

where (date_added > v_Last_Archive

or date_modified > v_Last_Archive)

and cm.dtcreated- gm.date_added> v_Datediff

group by crsmain_pk1) GM on GM.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(gg.pk1) GG

from gradebook_main gm

left join gradebook_grade gg on gm.pk1 = gg.gradebook_main_pk1

left join course_main cm on gm.crsmain_pk1 = cm.pk1

where (gg.date_added > v_Last_Archive

OR gg.date_modified > v_Last_Archive)

and cm.dtcreated- gg.date_added> v_Datediff

group by crsmain_pk1) GG on GG.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(qa.pk1) QA

from qti_asi_data qa

left join course_main cm on cm.pk1 = qa.crsmain_pk1

where (bbmd_date_added > v_Last_Archive

OR bbmd_date_modified > v_Last_Archive)

and cm.dtcreated- qa.bbmd_date_added> v_Datediff

group by crsmain_pk1) QA on QA.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(a.pk1) A

from attempt a

left join gradebook_grade gg on a.pk1 = gg.last_attempt_pk1

left join gradebook_main gm on gm.pk1 = gg.gradebook_main_pk1

left join course_main cm on cm.pk1 = gm.crsmain_pk1

where (a.attempt_date > v_Last_Archive

or a.date_modified > v_Last_Archive)

and cm.dtcreated- a.attempt_date > v_Datediff

group by crsmain_pk1) A on A.crsmain_pk1 = cm.pk1

left join (select co.owner_pk1, COUNT(CON.pk1) CONFERENCE_MAIN

from conference_owner CO

left join conference_main CON on CON.conference_owner_pk1 = CO.pk1

left join course_main cm on cm.pk1 = co.owner_pk1

where co.owner_table = 'COURSE_MAIN'

and (CON.dtcreated > v_Last_Archive

OR CON.dtmodified > v_Last_Archive)

and cm.dtcreated-con.dtcreated > v_Datediff

group by owner_pk1) ConM on ConM.OWNER_PK1 = cm.pk1

left join (select co.owner_pk1, COUNT(fr.pk1) FORUM_MAIN

from conference_owner CO

left join conference_main CON on CON.conference_owner_pk1 = CO.pk1

left join forum_main fr on fr.confmain_pk1 = CON.pk1

left join course_main cm on cm.pk1 = co.owner_pk1

where owner_table = 'COURSE_MAIN'

and (fr.dtcreated > v_Last_Archive

OR fr.dtmodified > v_Last_Archive)

and cm.dtcreated- fr.dtcreated > v_Datediff

group by owner_pk1) FM on FM.OWNER_PK1 = cm.pk1

left join (select co.owner_pk1, COUNT(mm.pk1) MSG_MAIN

from conference_owner CO

left join conference_main CON on CON.conference_owner_pk1 = CO.pk1

left join forum_main fr on fr.confmain_pk1 = CON.pk1

left join msg_main mm on mm.forummain_pk1 = fr.pk1

left join msg_main mm_reply on mm_reply.msgmain_pk1 = mm.pk1

left join course_main cm on cm.pk1 = co.owner_pk1

where owner_table = 'COURSE_MAIN'

and (mm.dtcreated > v_Last_Archive

OR mm.dtmodified > v_Last_Archive)

and cm.dtcreated- mm.dtcreated > v_Datediff

group by owner_pk1) MM on MM.OWNER_PK1 = cm.pk1

left join (select crsmain_pk1, COUNT(c.pk1) C

from calendar c

left join course_main cm on cm.pk1 = c.crsmain_pk1

where c.dtmodified > v_Last_Archive

and cm.dtcreated- c.dtmodified > v_Datediff

group by crsmain_pk1) C on C.crsmain_pk1 = cm.pk1

left join (select crsmain_pk1, COUNT(s.pk1) S

from staffinformation S

left join course_main cm on cm.pk1 = s.crsmain_pk1

where s.dtmodified > v_Last_Archive

and cm.dtcreated- s.dtmodified > v_Datediff

group by crsmain_pk1) S on S.crsmain_pk1 = cm.pk1

where nvl(CC.CC,0) + nvl(GM.GM,0) + nvl(GG.GG,0) + nvl(QA.QA,0) + nvl(A.A,0) + nvl(ConM.CONFERENCE_MAIN,0) + nvl(FM.FORUM_MAIN,0) + nvl(MM.MSG_MAIN,0) + nvl(S.S,0) + nvl(C.C,0) >= v_Number_of_New_Entities)

LOOP

dbms_output.put_line (rec.output);

END LOOP;

dbms_output.new_line();

end;

Page 56: Bb world 2011 capacity planning

Expense and Budget ManagementDatabase File Size

SELECT

DB_NAME(database_id) AS DatabaseName,

Name AS Logical_Name,

Physical_Name,

(size*8)/1024 SizeMB

FROM sys.master_files

order by SizeMB desc

Page 57: Bb world 2011 capacity planning

Expense and Budget ManagementDatabase File Size

select (select sum(bytes)/1024/1024 from dba_data_files)+

(select sum(bytes)/1024/1024 from dba_temp_files) "Size in MB" from dual;

Page 58: Bb world 2011 capacity planning

Expense and Budget ManagementTable Row Count and Sizes

select IDENTITY( int ) AS pk1, name into Table_List from sys.tables

CREATE TABLE Table_Results

(name nvarchar(256),

rows int,

reserved nvarchar(256),

data nvarchar(256),

index_size nvarchar(256),

unused nvarchar(256))

declare @pk1 int

declare @table nvarchar(256)

declare @end int

set @pk1 = 0

set @end = (select top 1 PK1 from Table_List order by pk1 Desc)

WHILE @pk1 < @end

begin

set @pk1 = @pk1 + 1

set @table = (select name from Table_List where pk1 = @pk1)

insert into Table_Results

exec sp_spaceused @table

end

select *

from table_results

drop table table_list

drop table table_results

Page 59: Bb world 2011 capacity planning

Expense and Budget ManagementTable Row Count and Sizes

Select OWNER, TABLE_NAME, TABLESPACE_NAME, NUM_ROWS, PCT_FREE , PCT_USED , (blocks*8/1024,2) as MB

from dba_tables

order by OWNER, TABLESPACE_NAME, TABLE_NAME;

Page 60: Bb world 2011 capacity planning

Expense and Budget ManagementTable growth rate (by year)

/* depending on the table, the dtcreated could need to be changed to timestamp */

select YEAR(dtcreated), COUNT(*)

from course_contents --Enter the table name here

group by YEAR(dtcreated)

Page 61: Bb world 2011 capacity planning

Expense and Budget ManagementTable growth rate (by year)

select TO_char(dtcreated,'YYYY') , COUNT(*)

from course_contents --Enter the table name here

group by TO_char(dtcreated,'YYYY') ;

Page 62: Bb world 2011 capacity planning

Expense and Budget ManagementTable growth rate (by month)

/* depending on the table, the dtcreated could need to be changed to timestamp */

select YEAR(dtcreated), MONTH(dtcreated), COUNT(*)

from course_main --Enter the table name here

group by YEAR(dtcreated), MONTH(dtcreated)

Page 63: Bb world 2011 capacity planning

Expense and Budget ManagementTable growth rate (by month)

select TO_char(dtcreated,'YYYY'), TO_char(dtcreated,'MM') , COUNT(*)

from course_contents --Enter the table name here

group by TO_char(dtcreated,'YYYY'), TO_char(dtcreated,'MM')

order by TO_char(dtcreated,'YYYY'), TO_char(dtcreated,'MM') ;

Page 64: Bb world 2011 capacity planning

Strategic Functional DecisionsWhat is the percent of enrollments from the previous term that have

completed a test online?

declare @start_date datetime

declare @end_date datetime

declare @TotalPopulation int

declare @TestingPopulation int

set @start_date = '2010-9-1 00:00:00:000'

set @end_date = '2011-9-1 00:00:00:000'

set @TotalPopulation = (select Count(distinct users_pk1)

from course_users cu

left join course_main cm on cm.pk1 = cu.crsmain_pk1

where role = 'S'

and dtcreated > @start_date

and dtcreated < @end_date)

set @TestingPopulation = (select Count(Distinct cu.users_pk1)

from course_users cu

left join gradebook_grade gg on gg.course_users_pk1 = cu.pk1

left join gradebook_main gm on gg.gradebook_main_pk1 = gm.pk1

left join course_main cm on cm.pk1 = cu.crsmain_pk1

where gm.qti_asi_data_pk1 > 0

and gg.first_attempt_pk1 > 0

and dtcreated > @start_date

and dtcreated < @end_date)

select @TestingPopulation as Online_Testing, @TotalPopulation - @TestingPopulation as Offline_Testing

Page 65: Bb world 2011 capacity planning

Strategic Functional DecisionsWhat is the percent of enrollments from the previous term that have

completed a test online?

set serveroutput on size 100000

declare v_start_date date;

v_end_date date;

v_TotalPopulation int;

v_TestingPopulation int;

Begin

dbms_output.enable(9999999);

dbms_output.new_line();

v_start_date := to_date('1-JAN-2010');

v_end_date := to_date('1-JAN-2012');

select Count(distinct users_pk1) into v_TotalPopulation

from course_users cu

left join course_main cm on cm.pk1 = cu.crsmain_pk1

where role = 'S'

and dtcreated > v_start_date

and dtcreated < v_end_date;

select Count(Distinct cu.users_pk1) into v_TestingPopulation

from course_users cu

left join gradebook_grade gg on gg.course_users_pk1 = cu.pk1

left join gradebook_main gm on gg.gradebook_main_pk1 = gm.pk1

left join course_main cm on cm.pk1 = cu.crsmain_pk1

where gm.qti_asi_data_pk1 > 0

and gg.first_attempt_pk1 > 0

and dtcreated > v_start_date

and dtcreated < v_end_date;

dbms_output.put_line (v_TestingPopulation || ',' || to_char(v_TotalPopulation - v_TestingPopulation));

--select v_TestingPopulation as Online_Testing, v_TotalPopulation - v_TestingPopulation as Offline_Testing;

end;

Page 66: Bb world 2011 capacity planning

Strategic Functional DecisionsHow many tests have been completed per enrollment?

declare @enrollment_start datetime

declare @enrollment_end datetime

set @enrollment_start = '2010-9-1 00:00:00:000'

set @enrollment_end = '2011-9-1 00:00:00:000'

select NumberOfTests, COUNT(NumberOfTests) NumberOfEnrollments

into #BinTests

from (

select AllStudents.users_pk1, NumberOfTests = Case

When TestingStudents.TheCount IS NULL THEN 0

When TestingStudents.TheCount > 0 THEN TestingStudents.TheCount

END

FROM (

select distinct users_pk1

from course_users

where role = 'S'

and enrollment_date > @enrollment_start

and enrollment_date < @enrollment_end) AllStudents

left join(

select cu.users_pk1, COUNT(gg.pk1) as TheCount

from course_users cu

left join gradebook_grade gg on gg.course_users_pk1 = cu.pk1

left join gradebook_main gm on gg.gradebook_main_pk1 = gm.pk1

where gm.qti_asi_data_pk1 > 0

and gg.first_attempt_pk1 > 0

and cu.enrollment_date > @enrollment_start

and cu.enrollment_date < @enrollment_end

group by cu.users_pk1) TestingStudents

on AllStudents.users_pk1 = TestingStudents.users_pk1) TestBin

group by NumberOfTests

declare @start int

declare @end int

declare @enrollments int

set @start = 0

set @end = (Select top 1 NumberOfTests from #BinTests order by NumberOfTests desc)

create table #Results(

Number_Of_Tests int,

Number_Of_Enrollments int)

While @start-1 < @end

Begin

set @enrollments = (select NumberOfEnrollments from #BinTests where NumberOfTests = @start)

insert into #Results

(Number_of_Tests, Number_Of_Enrollments)

values

(@start, @enrollments)

set @start = @start + 1

end

select Number_Of_Tests, Number_Of_Enrollments = Case

When Number_Of_Enrollments IS NULL THEN 0

When Number_Of_Enrollments >= 0 THEN Number_Of_Enrollments

End

from #Results

drop table #BinTests

drop table #Results

Page 67: Bb world 2011 capacity planning

Strategic Functional DecisionsHow many tests have been completed per enrollment?

set serveroutput on size 100000

declare

v_enrollment_start date;

v_enrollment_end date;

sql_stmt varchar(8000);

v_start int;

v_end int;

v_enrollments int;

Begin

dbms_output.enable(9999999);

dbms_output.new_line();

v_enrollment_start := to_date('2010-9-1 00:00:00', 'yyyy-mm-dd HH24:MI:SS');

v_enrollment_end := to_date('2011-9-1 00:00:00', 'yyyy-mm-dd HH24:MI:SS');

--sql_stmt :=

EXECUTE IMMEDIATE ' drop table BinTests';

sql_stmt :=''

|| 'create table '

|| 'BinTests as '

|| 'select NumberOfTests , COUNT(NumberOfTests) as NumberOfEnrollments '

|| 'from ( '

|| ' select AllStudents.users_pk1, nvl(TestingStudents.TheCount,0) NumberOfTests'

|| ' FROM ( '

|| ' select distinct users_pk1 '

|| ' from course_users '

|| ' where role = ''S'' '

|| ' and enrollment_date > ' || 'to_date('''||v_enrollment_start || '' ')'

|| ' and enrollment_date < ' || 'to_date('''||v_enrollment_end || '' ')' ||' ) AllStudents '

|| ' left join( '

|| ' select cu.users_pk1, COUNT(gg.pk1) as TheCount '

|| ' from course_users cu '

|| ' left join gradebook_grade gg on gg.course_users_pk1 = cu.pk1 '

|| ' left join gradebook_main gm on gg.gradebook_main_pk1 = gm.pk1 '

|| ' where gm.qti_asi_data_pk1 > 0 '

|| ' and gg.first_attempt_pk1 > 0 '

|| ' and cu.enrollment_date > ' || 'to_date('''||v_enrollment_start || ''')'

|| ' and cu.enrollment_date < ' || 'to_date('''||v_enrollment_end || '' ')'

|| ' group by cu.users_pk1) TestingStudents '

|| ' on AllStudents.users_pk1 = TestingStudents.users_pk1) TestBin '

|| 'group by NumberOfTests' ;

dbms_output.put_line (sql_stmt );

EXECUTE IMMEDIATE sql_stmt ;

EXCEPTION

WHEN OTHERS THEN NULL;

End;

/

set serveroutput on size 100000

declare

v_enrollment_start date;

v_enrollment_end date;

sql_stmt varchar(8000);

v_start int;

v_end int;

v_enrollments int;

Begin

dbms_output.enable(9999999);

dbms_output.new_line();

v_enrollment_start := to_date('2010-9-1 00:00:00', 'yyyy-mm-dd HH24:MI:SS');

v_enrollment_end := to_date('2011-9-1 00:00:00', 'yyyy-mm-dd HH24:MI:SS');

v_start := 0;

Select NumberOfTests into v_end from (select NumberOfTests from BinTests order by NumberOfTests desc) WHERE ROWNUM =1;

EXECUTE IMMEDIATE ' drop table Results';

EXECUTE IMMEDIATE ' create table Results ( Number_Of_Tests int, Number_Of_Enrollments int)';

EXCEPTION

WHEN OTHERS THEN NULL;

END;

/

set serveroutput on size 100000

declare

v_enrollment_start date;

v_enrollment_end date;

sql_stmt varchar(8000);

v_start int;

v_end int;

v_enrollments int;

Begin

dbms_output.enable(9999999);

dbms_output.new_line();

v_enrollment_start := to_date('2010-9-1 00:00:00', 'yyyy-mm-dd HH24:MI:SS');

v_enrollment_end := to_date('2011-9-1 00:00:00', 'yyyy-mm-dd HH24:MI:SS');

While v_start-1 < v_end

loop

select NumberOfEnrollments into v_enrollments from BinTests where NumberOfTests = v_start;

insert into Results

(Number_of_Tests, Number_Of_Enrollments)

values

( v_start, v_enrollments);

v_start := v_start + 1;

end loop;

dbms_output.new_line();

FOR rec IN (

select Number_Of_Tests, nvl(Number_Of_Enrollments,0) Number_Of_Enrollments from Results)

LOOP

dbms_output.put_line (rec.Number_Of_Tests || ',' || rec.Number_Of_Enrollments);

END LOOP;

dbms_output.new_line();

EXCEPTION

WHEN OTHERS THEN NULL;

--drop table BinTests

--drop table Results

END;

Page 68: Bb world 2011 capacity planning

Strategic Functional DecisionsHow many test questions were submitted at our peak hour?

SELECT count(pk1) TheCount,

cast(DATEPART(YEAR, bbmd_date_added) as varchar(4)) + '-' +

cast(DATEPART(MONTH, bbmd_date_added) as varchar(2))

from qti_result_data

group by DATEPART(YEAR, bbmd_date_added),

DATEPART(MONTH, bbmd_date_added)

order by DATEPART(YEAR, bbmd_date_added),

DATEPART(MONTH, bbmd_date_added)

Page 69: Bb world 2011 capacity planning

Strategic Functional DecisionsHow many test questions were submitted at our peak hour?

SELECT count(pk1) TheCount,

TO_char(bbmd_date_added,'YYYY') || '-' || TO_char(bbmd_date_added,'MM')

from qti_result_data

group by TO_char(bbmd_date_added,'YYYY'),

TO_char(bbmd_date_added,'MM')

order by TO_char(bbmd_date_added,'YYYY'),

TO_char(bbmd_date_added,'MM');

Page 70: Bb world 2011 capacity planning

Strategic Functional DecisionsHow many test questions were submitted at our peak hour?

SELECT top 25 count(pk1) TheCount,

cast(DATEPART(YEAR, bbmd_date_added) as varchar(4)) + '-' +

cast(DATEPART(MONTH, bbmd_date_added) as varchar(2)) + '-' +

cast(DATEPART(DAY, bbmd_date_added) as varchar(2)) + ' ' +

cast(DATEPART(HOUR, bbmd_date_added) as varchar(2)) + ':00'

from qti_result_data

group by DATEPART(YEAR, bbmd_date_added),

DATEPART(MONTH, bbmd_date_added),

DATEPART(DAY, bbmd_date_added),

DATEPART(HOUR, bbmd_date_added)

order by count(pk1) desc

Page 71: Bb world 2011 capacity planning

Strategic Functional DecisionsHow many test questions were submitted at our peak hour?

select * from

(SELECT count(pk1) TheCount,

TO_char(bbmd_date_added,'YYYY') || '-' || TO_char(bbmd_date_added,'MM') || '-' || TO_char(bbmd_date_added,'DD') || '-' || TO_char(bbmd_date_added,'HH')

from qti_result_data

group by TO_char(bbmd_date_added,'YYYY'),

TO_char(bbmd_date_added,'MM'),

TO_char(bbmd_date_added,'DD') ,

TO_char(bbmd_date_added,'HH')

order by count(pk1) desc

)

where rownum <26;

Page 72: Bb world 2011 capacity planning

Strategic Functional DecisionsTest question submission by hour of the day?

declare @start_date datetime

declare @end_date datetime

set @start_date = '2010-9-1 00:00:00:000'

set @end_date = '2011-9-1 00:00:00:000'

SELECT count(pk1) TheCount,

cast(DATEPART(hour, bbmd_date_added) as varchar(4)) TheHour

from qti_result_data

where bbmd_date_added > @start_date

and bbmd_date_added < @end_date

group by DATEPART(HOUR, bbmd_date_added)

order by DATEPART(HOUR, bbmd_date_added)

Page 73: Bb world 2011 capacity planning

Strategic Functional DecisionsTest question submission by hour of the day?

set serveroutput on size 100000

declare v_start_date date;

v_end_date date;

Begin

v_start_date := to_date('2010-9-1 00:00:00', 'yyyy-mm-dd HH24:MI:SS');

v_end_date := to_date('2011-9-1 00:00:00', 'yyyy-mm-dd HH24:MI:SS');

dbms_output.enable(9999999);

dbms_output.new_line();

FOR rec IN (

SELECT count(pk1) TheCount,

TO_char(bbmd_date_added,'HH24') TheHour

from qti_result_data

where bbmd_date_added > v_start_date

and bbmd_date_added < v_end_date

group by TO_char(bbmd_date_added,'HH24')

order by TO_char(bbmd_date_added,'HH24'))

LOOP

dbms_output.put_line (to_char(rec.TheCount));

END LOOP;

dbms_output.new_line();

end;

Page 74: Bb world 2011 capacity planning

Strategic Functional DecisionsTest question Submission by day of the week?

declare @start_date datetime

declare @end_date datetime

set @start_date = '2010-9-1 00:00:00:000'

set @end_date = '2011-9-1 00:00:00:000'

SELECT count(pk1) TheCount, TheDay = Case

when cast(DATEPART(DW, bbmd_date_added) as varchar(4)) = 1 then 'Sunday'

when cast(DATEPART(DW, bbmd_date_added) as varchar(4)) = 2 then 'Monday'

when cast(DATEPART(DW, bbmd_date_added) as varchar(4)) = 3 then 'Tuesday'

when cast(DATEPART(DW, bbmd_date_added) as varchar(4)) = 4 then 'Wednesday'

when cast(DATEPART(DW, bbmd_date_added) as varchar(4)) = 5 then 'Thursday'

when cast(DATEPART(DW, bbmd_date_added) as varchar(4)) = 6 then 'Friday'

when cast(DATEPART(DW, bbmd_date_added) as varchar(4)) = 7 then 'Saturday'

end

from qti_result_data

where bbmd_date_added > @start_date

and bbmd_date_added < @end_date

group by DATEPART(DW, bbmd_date_added)

order by DATEPART(DW, bbmd_date_added) asc

Page 75: Bb world 2011 capacity planning

Strategic Functional DecisionsTest question Submission by day of the week?

--v_start_date := '2010-9-1 00:00:00:000'

--v_end_date := '2011-9-1 00:00:00:000'

SELECT count(pk1) TheCount, to_char(to_date (bbmd_date_added, 'yyyy-mm-dd HH24:MI:SS'),'DAY')

from qti_result_data

where bbmd_date_added > to_date('2010-9-1', 'yyyy-mm-dd')

and bbmd_date_added < to_date('2011-9-1', 'yyyy-mm-dd')

group by to_char(to_date (bbmd_date_added , 'yyyy-mm-dd HH24:MI:SS'),'DAY')

order by to_char(to_date (bbmd_date_added , 'yyyy-mm-dd HH24:MI:SS'),'DAY') asc

Page 76: Bb world 2011 capacity planning

Strategic Functional DecisionsDetermine CPU and I/O cost of testing (SQL server)

SELECT p.name AS[SP_Name],

ps.total_worker_time AS[Total_Worker_Time],

ps.total_physical_reads AS[Total_Physical_Reads],

ps.total_logical_reads,

ps.total_logical_writes AS[Total_Logical_Writes],

(ps.total_logical_reads +ps.total_logical_writes) /ps.execution_count AS[TOTAL_IO],

ps.execution_count,

ISNULL(ps.execution_count/DATEDIFF(Second,ps.cached_time,GETDATE()),0)AS[Calls/Second],

ps.total_elapsed_time,

ps.last_worker_time,

ps.total_elapsed_time/ps.execution_count AS[avg_elapsed_time],

ps.last_elapsed_time,

ps.last_execution_time,

ps.cached_time,

qs.text Query

FROM sys.procedures AS p,

sys.dm_exec_procedure_stats AS ps

cross apply sys.dm_exec_sql_text (ps.sql_handle) AS qs

WHERE p.[object_id] =ps.[object_id]

and ps.database_id =DB_ID()

--and p.name = 'qti_result_data_cr' -- Enter the name of the stored procedure

ORDER BY ps.last_worker_time DESC;

Page 77: Bb world 2011 capacity planning

Strategic Functional DecisionsDetermine CPU and I/O cost of testing (SQL server)

Typically, you would view the AWR data through Oracle Enterprise Manager screens or AWR reports. However, you can view the statistics with the following views:

V$ACTIVE_SESSION_HISTORY

This view displays active database session activity, sampled once every second. See "Active Session History (ASH)".

V$ metric views provide metric data to track the performance of the system

The metric views are organized into various groups, such as event, event class, system, session, service, file, and tablespace metrics. These groups are identified in the V$METRICGROUP view.

DBA_HIST views

The DBA_HIST views contain historical data stored in the database. This group of views includes:

DBA_HIST_ACTIVE_SESS_HISTORY displays the history of the contents of the in-memory active session history for recent system activity.

DBA_HIST_BASELINE displays information about the baselines captured on the system

DBA_HIST_DATABASE_INSTANCE displays information about the database environment

DBA_HIST_SNAPSHOT displays information on snapshots in the system

DBA_HIST_SQL_PLAN displays the SQL execution plans

DBA_HIST_WR_CONTROL displays the settings for controlling AWR

Page 78: Bb world 2011 capacity planning

Strategic Functional DecisionsDetermine CPU and I/O cost of testing (SQL server)

SELECT SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1,((CASE qs.statement_end_offsetWHEN -1 THEN DATALENGTH(qt.TEXT)ELSE qs.statement_end_offsetEND - qs.statement_start_offset)/2)+1) Query,qs.execution_count,qs.total_logical_reads, qs.last_logical_reads,qs.total_logical_writes, qs.last_logical_writes, (qs.total_logical_reads +qs.total_logical_writes) /qs.execution_count AS[AVG_IO],qs.total_worker_time 'Total_CPU_Time',qs.last_worker_time 'Last_CPU_Time',qs.total_elapsed_time/1000000 total_elapsed_time_in_S,qs.last_elapsed_time/1000000 last_elapsed_time_in_S,qs.last_execution_time,qs.creation_time,qp.query_planFROM sys.dm_exec_query_stats qsCROSS APPLY sys.dm_exec_sql_text(qs.sql_handle) qtCROSS APPLY sys.dm_exec_query_plan(qs.plan_handle) qpWHERE SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1,((CASE qs.statement_end_offsetWHEN -1 THEN DATALENGTH(qt.TEXT)ELSE qs.statement_end_offsetEND - qs.statement_start_offset)/2)+1) LIKE '%qti%' -- Insert the query you are interested in findingORDER BY qs.last_execution_time DESC

Page 79: Bb world 2011 capacity planning

Strategic Functional DecisionsDetermine CPU and I/O cost of testing (SQL server)

Typically, you would view the AWR data through Oracle Enterprise Manager screens or AWR reports. However, you can view the statistics with the following views:

V$ACTIVE_SESSION_HISTORY

This view displays active database session activity, sampled once every second. See "Active Session History (ASH)".

V$ metric views provide metric data to track the performance of the system

The metric views are organized into various groups, such as event, event class, system, session, service, file, and tablespace metrics. These groups are identified in the V$METRICGROUP view.

DBA_HIST views

The DBA_HIST views contain historical data stored in the database. This group of views includes:

DBA_HIST_ACTIVE_SESS_HISTORY displays the history of the contents of the in-memory active session history for recent system activity.

DBA_HIST_BASELINE displays information about the baselines captured on the system

DBA_HIST_DATABASE_INSTANCE displays information about the database environment

DBA_HIST_SNAPSHOT displays information on snapshots in the system

DBA_HIST_SQL_PLAN displays the SQL execution plans

DBA_HIST_WR_CONTROL displays the settings for controlling AWR

Page 80: Bb world 2011 capacity planning

Strategic Functional DecisionsDetermine I/O cost of question submission (SQL server)

SELECT p.name AS[SP_Name],

(ps.total_logical_reads +ps.total_logical_writes) /ps.execution_count AS AVG_IO

FROM sys.procedures AS p,

sys.dm_exec_procedure_stats AS ps

cross apply sys.dm_exec_sql_text (ps.sql_handle) AS qs

WHERE p.[object_id] =ps.[object_id]

and ps.database_id =DB_ID()

and p.name = 'qti_result_data_cr'

ORDER BY (ps.total_logical_reads +ps.total_logical_writes) /ps.execution_count DESC;

Page 81: Bb world 2011 capacity planning

Strategic Functional DecisionsDetermine I/O cost of question submission (SQL server)

please look at AWR report

sear qti_result_data_cr

Page 82: Bb world 2011 capacity planning

Strategic Functional DecisionsDetermine IO cost of all cached stored procedures

SELECT p.name AS[SP_Name],

(ps.total_logical_reads +ps.total_logical_writes) /ps.execution_count AS AVG_IO

FROM sys.procedures AS p,

sys.dm_exec_procedure_stats AS ps

cross apply sys.dm_exec_sql_text (ps.sql_handle) AS qs

WHERE p.[object_id] =ps.[object_id]

and ps.database_id =DB_ID()

ORDER BY (ps.total_logical_reads +ps.total_logical_writes) /ps.execution_count DESC;

Page 83: Bb world 2011 capacity planning

Strategic Functional DecisionsDetermine IO cost of all cached stored procedures

--look at AWR report

set pagesize 60;

column executions format 999,999,999;

column Mem_used format 999,999,999;

SELECT SUBSTR(owner,1,10) Owner,

SUBSTR(type,1,12) Type,

SUBSTR(name,1,20) Name,

executions,

sharable_mem Mem_used,

SUBSTR(kept||' ',1,4) "Kept?"

FROM v$db_object_cache

WHERE type in ('PROCEDURE','PACKAGE BODY','PACKAGE')

ORDER BY executions desc;

HERE IS THE OUTPUT OF MEMORY.SQL:

SQL> @memory

Page 84: Bb world 2011 capacity planning

Strategic Functional DecisionsDetermine total IO cost of all cached stored procedures

SELECT p.name AS[SP_Name],

(ps.total_logical_reads +ps.total_logical_writes) AS TOTAL_IO

FROM sys.procedures AS p,

sys.dm_exec_procedure_stats AS ps

cross apply sys.dm_exec_sql_text (ps.sql_handle) AS qs

WHERE p.[object_id] =ps.[object_id]

and ps.database_id =DB_ID()

ORDER BY (ps.total_logical_reads +ps.total_logical_writes) DESC;

Page 85: Bb world 2011 capacity planning

Strategic Functional DecisionsDetermine total IO cost of all cached stored procedures

AWR report

Page 86: Bb world 2011 capacity planning

Strategic Functional DecisionsQuery that compares the test taking activity cost vs. to other activity

select 'QTI_IO' as TYPE, SUM(TOTAL_LOGICAL_READS + TOTAL_LOGICAL_WRITES) IO

FROM (SELECT SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1,

((CASE qs.statement_end_offset

WHEN -1 THEN DATALENGTH(qt.TEXT)

ELSE qs.statement_end_offset

END - qs.statement_start_offset)/2)+1) Query,

qs.execution_count,

qs.total_logical_reads, qs.last_logical_reads,

qs.total_logical_writes, qs.last_logical_writes, (qs.total_logical_reads +qs.total_logical_writes) /qs.execution_count AS[AVG_IO],

qs.total_worker_time 'Total_CPU_Time',

qs.last_worker_time 'Last_CPU_Time',

qs.total_elapsed_time/1000000 total_elapsed_time_in_S,

qs.last_elapsed_time/1000000 last_elapsed_time_in_S,

qs.last_execution_time,

qs.creation_time,

qp.query_plan

FROM sys.dm_exec_query_stats qs

CROSS APPLY sys.dm_exec_sql_text(qs.sql_handle) qt

CROSS APPLY sys.dm_exec_query_plan(qs.plan_handle) qp

WHERE SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1, ((CASE qs.statement_end_offset WHEN -1 THEN DATALENGTH(qt.TEXT) ELSE qs.statement_end_offset END - qs.statement_start_offset)/2)+1)

LIKE '%qti%' -- Insert the query you are interested in finding

and SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1, ((CASE qs.statement_end_offset WHEN -1 THEN DATALENGTH(qt.TEXT) ELSE qs.statement_end_offset END - qs.statement_start_offset)/2)+1)

NOT LIKE '%sys.dm%'

--and qs.last_execution_time + .005 > GETDATE()

)QTI_IO

UNION

select 'NON_QTI_IO' as TYPE, SUM(TOTAL_LOGICAL_READS + TOTAL_LOGICAL_WRITES) IO

FROM (SELECT SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1,

((CASE qs.statement_end_offset

WHEN -1 THEN DATALENGTH(qt.TEXT)

ELSE qs.statement_end_offset

END - qs.statement_start_offset)/2)+1) Query,

qs.execution_count,

qs.total_logical_reads, qs.last_logical_reads,

qs.total_logical_writes, qs.last_logical_writes, (qs.total_logical_reads +qs.total_logical_writes) /qs.execution_count AS[AVG_IO],

qs.total_worker_time 'Total_CPU_Time',

qs.last_worker_time 'Last_CPU_Time',

qs.total_elapsed_time/1000000 total_elapsed_time_in_S,

qs.last_elapsed_time/1000000 last_elapsed_time_in_S,

qs.last_execution_time,

qs.creation_time,

qp.query_plan

FROM sys.dm_exec_query_stats qs

CROSS APPLY sys.dm_exec_sql_text(qs.sql_handle) qt

CROSS APPLY sys.dm_exec_query_plan(qs.plan_handle) qp

WHERE SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1, ((CASE qs.statement_end_offset WHEN -1 THEN DATALENGTH(qt.TEXT) ELSE qs.statement_end_offset END - qs.statement_start_offset)/2)+1)

NOT LIKE '%qti%' -- Insert the query you are interested in finding

and SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1, ((CASE qs.statement_end_offset WHEN -1 THEN DATALENGTH(qt.TEXT) ELSE qs.statement_end_offset END - qs.statement_start_offset)/2)+1)

NOT LIKE '%sys.dm%'

--and qs.last_execution_time + .005 > GETDATE()

)NON_QTI_IO

Page 87: Bb world 2011 capacity planning

Strategic Functional DecisionsQuery that compares the test taking activity cost vs. to other activity

AWR report

and v$sql, sqlarea

on qti_result_data_cr

Page 88: Bb world 2011 capacity planning

Strategic Functional DecisionsQuery that joins the QTI tables (bbmd_data_added) with the cost of the

queries associated with the insert

declare @start_date datetime

declare @end_date datetime

declare @question_io int

set @start_date = '2010-9-1 00:00:00:000'

set @end_date = '2011-9-1 00:00:00:000'

set @question_io = (SELECT ps.last_logical_reads + ps.last_logical_writes Current_IO

FROM sys.procedures AS p,

sys.dm_exec_procedure_stats AS ps

cross apply sys.dm_exec_sql_text (ps.sql_handle) AS qs

WHERE p.[object_id] =ps.[object_id]

and ps.database_id =DB_ID()

and p.name = 'qti_result_data_cr')

SELECT count(pk1) * @question_io Test_Question_IO, cast(DATEPART(YEAR, bbmd_date_added) as varchar(4)) + '-' +

cast(DATEPART(MONTH, bbmd_date_added) as varchar(2)) + '-' +

cast(DATEPART(DAY, bbmd_date_added) as varchar(2)) TheDate

from qti_result_data

where bbmd_date_added > @start_date

and bbmd_date_added < @end_date

group by DATEPART(YEAR, bbmd_date_added),

DATEPART(MONTH, bbmd_date_added),

DATEPART(DAY, bbmd_date_added)

order by DATEPART(YEAR, bbmd_date_added),

DATEPART(MONTH, bbmd_date_added),

DATEPART(DAY, bbmd_date_added)

Page 89: Bb world 2011 capacity planning

Strategic Functional DecisionsQuery that joins the QTI tables (bbmd_data_added) with the cost of the

queries associated with the insert

AWR report

and v$sql, sqlarea

on qti_result_data_cr

Page 90: Bb world 2011 capacity planning

Strategic Functional DecisionsCreate a logging script

declare @ts_now bigint

declare @start int

declare @end int

declare @Start_time datetime

declare @End_time datetime

declare @Bb_Activity int

declare @QTI_RESULTS_Activity int

set @ts_now = (SELECT cpu_ticks/(cpu_ticks/ms_ticks)FROM sys.dm_os_sys_info);

SELECT TOP(256) SQLProcessUtilization AS [SQL_Server_Process_CPU_Utilization],

SystemIdle AS [System_Idle_Process],

100 - SystemIdle - SQLProcessUtilization AS [Other_Process_CPU_Utilization],

DATEADD(ms, -1 * (@ts_now - [timestamp]), GETDATE()) AS [start_Time],

DATEADD(minute, 1, DATEADD(ms, -1 * (@ts_now - [timestamp]), GETDATE())) AS [end_Time],

IDENTITY( int ) AS TheCount

into #cpu

FROM (SELECT record.value('(./Record/@id)[1]', 'int') AS record_id,

record.value('(./Record/SchedulerMonitorEvent/SystemHealth/SystemIdle)[1]', 'int') AS [SystemIdle],

record.value('(./Record/SchedulerMonitorEvent/SystemHealth/ProcessUtilization)[1]', 'int') AS [SQLProcessUtilization], [timestamp]

FROM (SELECT [timestamp], CONVERT(xml, record) AS [record]

FROM sys.dm_os_ring_buffers

WHERE ring_buffer_type = N'RING_BUFFER_SCHEDULER_MONITOR'

AND record LIKE N'%<SystemHealth>%') AS x) AS y

ORDER BY record_id DESC

set @start = 0

set @end = (select MAX(TheCount) from #cpu)

CREATE TABLE [dbo].[#cpu_Activity](

[Activity_Accumulator_Activity] [int] NULL,

[QTI_RESULTS_Activity] [int] NULL,

[SQL_Server_Process_CPU_Utilization] [int] NULL,

[System_Idle_Process] [int] NULL,

[Other_Process_CPU_Utilization] [int] NULL,

[start_Time] [datetime] NULL,

[end_Time] [datetime] NULL,

[TheCount] [int] NULL)

WHILE @start < @end

BEGIN

SET @start = @start + 1

SET @Start_time = (select Start_Time from #cpu where TheCount = @start)

SET @End_time = (select End_Time from #cpu where TheCount = @start)

set @Bb_Activity = (select COUNT(*) from activity_accumulator where timestamp > @Start_time and timestamp < @End_time)

set @QTI_RESULTS_Activity = (select COUNT(*) from qti_result_data where bbmd_date_modified > @Start_time and bbmd_date_modified < @End_time)

Insert into #cpu_Activity

SELECT @Bb_Activity, @QTI_RESULTS_Activity, *

from #cpu

where thecount = @start

end

select *

from #cpu_activity

drop table #cpu;

drop table #cpu_activity;

Page 91: Bb world 2011 capacity planning

Strategic Functional DecisionsCreate a logging script

AWR report, v$sql

select ... rom activity_accmultor where event_type ='login';

Page 92: Bb world 2011 capacity planning

Strategic Functional DecisionsCreate a logging script

CREATE TABLE [dbo].[#FILE_IO](

[name] [sysname] NULL,

[num_of_bytes_read] [bigint] NOT NULL,

[num_of_bytes_written] [bigint] NOT NULL,

[num_of_reads] [bigint] NOT NULL,

[num_of_writes] [bigint] NOT NULL,

[size_on_disk_bytes] [bigint] NOT NULL

) ON [PRIMARY]

declare @start int

declare @end int

set @start = 5

set @end = (select top 1 database_id

from sys.master_files

where database_id > 5

order by database_id desc)

while @start < @end

begin

insert into #FILE_IO

select name, num_of_bytes_read, num_of_bytes_written, num_of_reads, num_of_writes, size_on_disk_bytes

from sys.dm_io_virtual_file_stats(@start,NULL) s

left join sys.master_files f on s.database_id = f.database_id and s.file_id = f.file_id

set @start = @start + 1

end

select *

from #FILE_IO

drop table #FILE_IO

Page 93: Bb world 2011 capacity planning

Strategic Functional DecisionsCreate a logging script

AWR report, v$sql

select ... rom activity_accmultor where event_type ='login';

Page 94: Bb world 2011 capacity planning

Strategic Functional DecisionsCreate a logging script

SELECT 'TEST QUESTION' Type,

SUM(qs.execution_count) Execution_Count,

SUM(qs.total_logical_reads) Total_Reads,

SUM(qs.total_logical_writes) Total_Writes,

SUM(qs.total_worker_time) Total_CPU

FROM sys.dm_exec_query_stats qs

CROSS APPLY sys.dm_exec_sql_text(qs.sql_handle) qt

CROSS APPLY sys.dm_exec_query_plan(qs.plan_handle) qp

WHERE SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1,

((CASE qs.statement_end_offset

WHEN -1 THEN DATALENGTH(qt.TEXT)

ELSE qs.statement_end_offset

END - qs.statement_start_offset)/2)+1) LIKE '%INSERT INTO QTI_RESULT_DATA%' --Enter a portion of the query text you are interested in

and SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1,

((CASE qs.statement_end_offset

WHEN -1 THEN DATALENGTH(qt.TEXT)

ELSE qs.statement_end_offset

END - qs.statement_start_offset)/2)+1) NOT LIKE 'SELECT SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1,%'

UNION

SELECT 'OTHER TRANSACTIONS' Type,

SUM(qs.execution_count) Execution_Count,

SUM(qs.total_logical_reads) Total_Reads,

SUM(qs.total_logical_writes) Total_Writes,

SUM(qs.total_worker_time) Total_CPU

FROM sys.dm_exec_query_stats qs

CROSS APPLY sys.dm_exec_sql_text(qs.sql_handle) qt

CROSS APPLY sys.dm_exec_query_plan(qs.plan_handle) qp

WHERE SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1,

((CASE qs.statement_end_offset

WHEN -1 THEN DATALENGTH(qt.TEXT)

ELSE qs.statement_end_offset

END - qs.statement_start_offset)/2)+1) NOT LIKE '%INSERT INTO QTI_RESULT_DATA%' --Enter a portion of the query text you are interested in

and SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1,

((CASE qs.statement_end_offset

WHEN -1 THEN DATALENGTH(qt.TEXT)

ELSE qs.statement_end_offset

END - qs.statement_start_offset)/2)+1) NOT LIKE 'SELECT SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1,%'

Page 95: Bb world 2011 capacity planning

Strategic Functional DecisionsCreate a logging script

AWR report,

and use

v$sql, sqlarea to find INSERT INTO QTI_RESULT_DATA%'