Skip to content

Export option for teams report useractivityuserdetail [options]#1061

Closed
sprider wants to merge 5 commits intopnp:devfrom
sprider:exportteamsuseractivity
Closed

Export option for teams report useractivityuserdetail [options]#1061
sprider wants to merge 5 commits intopnp:devfrom
sprider:exportteamsuseractivity

Conversation

@sprider
Copy link
Copy Markdown
Contributor

@sprider sprider commented Aug 16, 2019

@VelinGeorgiev,

I have completed the export logic based on the comments provided by you at issue #1038.

Let us start the review and I can work on your feedbacks in parallel. Also I will work on code coverage items at teams-report-useractivityuserdetail.spec.ts file once we finish the review for teams-report-useractivityuserdetail.ts and report-useractivityuserdetail.md files.

Thank you.

@sprider sprider changed the title initial commit Export option for teams report useractivityuserdetail [options] Aug 16, 2019
Copy link
Copy Markdown
Contributor

@VelinGeorgiev VelinGeorgiev left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@sprider , the tests are failing.
I have added some initial comments for you. Thanks for looking into this.

`-p, --period <period>`|The length of time over which the report is aggregated. Supported values `D7, D30, D90, D180`. Specify the `period` or `date`, but not both.
`-d, --date [date]`|The date for which you would like to view the users who performed any activity. Supported date format is `YYYY-MM-DD`. Specify the `date` or `period`, but not both.
`-f, --outputFile [outputFile]`|Path to the file where the upgrade report should be stored in.
`-o, --output [output]`|Output type. `csv|json|text`. Default `csv`
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The output option is there for every command and by default is text. I would suggest you keep it the same as the rest of the commands where it defaults to text and the options are in the following order text,json,csv. See how Waldek did it here: https://github.com/pnp/office365-cli/pull/1037/files

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have fixed this in the latest commit.

period?: string;
date?: string;
outputFile?: string;
output?: string;
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There is no need to introduce new output option since it is already introduced by the parent class, you just have to reuse it. See https://github.com/pnp/office365-cli/pull/1037/files

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have fixed this in the latest commit.

telemetryProps.period = typeof args.options.period !== 'undefined';
telemetryProps.date = typeof args.options.date !== 'undefined';
telemetryProps.outputFile = typeof args.options.outputFile !== 'undefined';
telemetryProps.output = typeof args.options.output !== 'undefined';
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There is no need to log telemetry for output since it is already captured by the parent class. See https://github.com/pnp/office365-cli/pull/1037/files

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have fixed this in the latest commit.


let content: string = '';

if (args.options.outputFile.toLowerCase().endsWith('.json'))
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You should check if the --output option is set to json instead of checking for extension.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have fixed this in the latest commit. Just an FYI here user can export the report data to the specified path in csv,txt and json formats

.then((res: any): void => {
cmd.log(res);

if (args.options.outputFile) {
Copy link
Copy Markdown
Contributor

@VelinGeorgiev VelinGeorgiev Aug 16, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The --outputFile check should come after checking the --output option. We should be able to print json on the screen in case of json being specified in the --output and not --outputFile specified. We should be also able to save that json to a file in case --outputFile and --outputFile is specified as well. Something similar is done by Waldek here: https://github.com/pnp/office365-cli/pull/1037/files

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have fixed this in the latest commit. Just an FYI here user can export the report data to the specified path in csv,txt and json formats

return 'Specified outputFile path where to save the file does not exist';
}

if (args.options.outputFile && args.options.output && args.options.output.toLowerCase() === 'csv' && !args.options.outputFile.toLowerCase().endsWith('.csv')) {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I do not think the extension matters as long as the have --output option specified.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have fixed this in the latest commit but do we need to validate the below scenario where output is csv and path ends with json

teams report useractivityuserdetail --period D7 --output csv --outputFile '/Users/josephvelliah/Desktop/teams-report-useractivityuserdetail.json'

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My opinion is that we do not have to validate the extension nor the name for the specified file. The user can name it whatever, he/she will get content in json format when the --output option is set to json.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure, Thank you for the clarification.

return 'Specified outputFile path should be csv file extension';
}

if (args.options.outputFile && args.options.output && args.options.output.toLowerCase() === 'json' && !args.options.outputFile.toLowerCase().endsWith('.json')) {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I do not think the extension matters as long as the have --output option specified.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have fixed this in the latest commit but do we need to validate the below scenario where output is csv and path ends with json

teams report useractivityuserdetail --period D7 --output csv --outputFile '/Users/josephvelliah/Desktop/teams-report-useractivityuserdetail.json'

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My opinion is that we do not have to validate the extension nor the name for the specified file. The user can name it whatever, he/she will get content in json format when the --output option is set to json.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure, Thank you for the clarification.

return 'Specified outputFile path should be json file extension';
}

if (args.options.outputFile && args.options.output && args.options.output.toLowerCase() === 'text' && !args.options.outputFile.toLowerCase().endsWith('.txt')) {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I do not think the extension matters as long as the have --output option specified.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have fixed this in the latest commit but do we need to validate the below scenario where output is csv and path ends with json

teams report useractivityuserdetail --period D7 --output csv --outputFile '/Users/josephvelliah/Desktop/teams-report-useractivityuserdetail.json'

for July 13, 2019
${commands.TEAMS_REPORT_USERACTIVITYUSERDETAIL} --date 2019-07-13

Gets details about Microsoft Teams user activity by user for the last week and exports the report data in the specified path in csv format
Copy link
Copy Markdown
Contributor

@VelinGeorgiev VelinGeorgiev Aug 16, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Seems like you've build functionality for json output/export, but your example is with csv. Could you please align?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have fixed this in the latest commit.

Gets details about Microsoft Teams user activity by user for the last week and exports the report data in the specified path in csv format

```sh
teams report useractivityuserdetail --period D7 --outputFile '/Users/josephvelliah/Desktop/teams-report-useractivityuserdetail.csv'
Copy link
Copy Markdown
Contributor

@VelinGeorgiev VelinGeorgiev Aug 16, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Seems like you've build functionality for json output/export, but your example is with csv. Could you please align?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have fixed this in the latest commit.

@sprider
Copy link
Copy Markdown
Contributor Author

sprider commented Aug 16, 2019

@VelinGeorgiev
Please guide me on the unit test case for this method as well.
Screen Shot 2019-08-16 at 7 57 35 AM

@VelinGeorgiev
Copy link
Copy Markdown
Contributor

Joseph you will have to do a test with at least two rows of data to cover those lines

@sprider
Copy link
Copy Markdown
Contributor Author

sprider commented Aug 17, 2019

Joseph you will have to do a test with at least two rows of data to cover those lines

@VelinGeorgiev Sure, this is done.

@sprider
Copy link
Copy Markdown
Contributor Author

sprider commented Aug 17, 2019

@VelinGeorgiev
This is complete and ready for your review but ci/circleci: test shows failed.

My local npm test shows 100%. Do I need to modify anything?

Screen Shot 2019-08-17 at 10 46 25 AM

@VelinGeorgiev
Copy link
Copy Markdown
Contributor

Seems line 74 fails on the build machine. https://circleci.com/gh/pnp/office365-cli/2409?utm_campaign=vcs-integration-link&utm_medium=referral&utm_source=github-build-link.

You can do npm run clean + npm run build + npm t on all the tests to see if fresh build might not fail on your pc.

@sprider
Copy link
Copy Markdown
Contributor Author

sprider commented Aug 17, 2019

Seems line 74 fails on the build machine. https://circleci.com/gh/pnp/office365-cli/2409?utm_campaign=vcs-integration-link&utm_medium=referral&utm_source=github-build-link.

You can do npm run clean + npm run build + npm t on all the tests to see if fresh build might not fail on your pc.

@VelinGeorgiev
I did a fresh build and I am getting 100% and all looks good.

If I am not wrong, circleci is trying to find the path "/Users/josephvelliah/Desktop" to save the file

Please let me know how to proceed or mock this.

Screen Shot 2019-08-17 at 12 09 12 PM

@VelinGeorgiev
Copy link
Copy Markdown
Contributor

Joseph @sprider , to fix that you should fake the fs.writeFileSync function to return something instead of actually try to read from the hard drive. There is an example how to fake it here in these tests https://github.com/pnp/office365-cli/blob/c13ba0388ebc1579a6ae727783350bb4466e3cd1/src/o365/azmgmt/commands/flow/flow-export.spec.ts#L211

Have a look how Waldek did it and you can try to do it the same way.

@coveralls
Copy link
Copy Markdown

Coverage Status

Coverage remained the same at 100.0% when pulling d177723 on sprider:exportteamsuseractivity into 6ce20cb on pnp:dev.

@sprider
Copy link
Copy Markdown
Contributor Author

sprider commented Aug 21, 2019

Joseph @sprider , to fix that you should fake the fs.writeFileSync function to return something instead of actually try to read from the hard drive. There is an example how to fake it here in these tests

https://github.com/pnp/office365-cli/blob/c13ba0388ebc1579a6ae727783350bb4466e3cd1/src/o365/azmgmt/commands/flow/flow-export.spec.ts#L211

Have a look how Waldek did it and you can try to do it the same way.

@VelinGeorgiev I have fixed the issues as per your suggestion. Could you please review and merge this? Thank you.

Copy link
Copy Markdown
Contributor

@VelinGeorgiev VelinGeorgiev left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@sprider very well done! I tested the command and everything worked. This is the branch from where we will merge it.

I had to make some cosmetic changes. You can find my comments above.

if(args.options.outputFile)
{
fs.writeFileSync(args.options.outputFile, content, 'binary');
cmd.log(`File saved to path '${args.options.outputFile}'`);
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I added extra condition so that message will show in verbose mode only so the code looks like:

if (this.verbose) {
 cmd.log(`File saved to path '${args.options.outputFile}'`);
}

This follows the same pattern we have in other commands like file-get

{
let reportdata = this.getJsonReport(res);
content = JSON.stringify(reportdata);
cmd.log(reportdata);
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I added extra condition so that log should show in case user has not specified outputFile so the code looks like:

if (!args.options.outputFile) {
            cmd.log(reportdata);
 }

This follows the same pattern we have in other commands like file-get where no output on the screen is shown, but just file is generated.

${commands.TEAMS_REPORT_USERACTIVITYUSERDETAIL} --date 2019-07-13

Gets details about Microsoft Teams user activity by user for the last week and exports the report data in the specified path in json format
${commands.TEAMS_REPORT_USERACTIVITYUSERDETAIL} --period D7 --output json --outputFile '/Users/josephvelliah/Desktop/teams-report-useractivityuserdetail.json'
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

/Users/josephvelliah/Desktop/teams-report-useractivityuserdetail.json changed to C:/report.json to shorten the message for smaller screens.


if(args.options.outputFile)
{
fs.writeFileSync(args.options.outputFile, content, 'binary');
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

binary changed to utf8 since when exported to CSV the report had weird char in the first column

image

else
{
content = res;
cmd.log(content);
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I added extra condition so that log should show in case user has not specified outputFile so the code looks like:

if (!args.options.outputFile) {
            cmd.log(content);
 }

This follows the same pattern we have in other commands like file-get where no output on the screen is shown, but just file is generated.

Gets details about Microsoft Teams user activity by user
for July 13, 2019
${commands.TEAMS_REPORT_USERACTIVITYUSERDETAIL} --date 2019-07-13

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I added another example showing how to export in csv as well

Gets details about Microsoft Teams user activity by user for the last week
      and exports the report data in the specified path in csv format
        ${commands.TEAMS_REPORT_USERACTIVITYUSERDETAIL} --period D7 --output csv --outputFile 'C:/report.csv'


return Promise.reject('Invalid request');
});
sinon.stub(fs, 'writeFileSync').callsFake(writeFileSyncFake);
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I assigned that stub to a var so I can tested later like

const fileStub: sinon.SinonStub = sinon.stub(fs, 'writeFileSync').callsFake(writeFileSyncFake);

assert.equal(requestStub.lastCall.args[0].headers["accept"], 'application/json;odata.metadata=none');
assert.equal(requestStub.lastCall.args[0].json, true);
assert(cmdInstanceLogSpy.calledWith(`File saved to path '/Users/josephvelliah/Desktop/teams-report-useractivityuserdetail.json'`));
done();
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I added extra assets to check if the writeFileSync is actually been called. This will verify that file will be created.

assert.equal(fileStub.called, true);

@VelinGeorgiev
Copy link
Copy Markdown
Contributor

Thank you Jospeh @sprider ! Merged manually 🚀

@sprider
Copy link
Copy Markdown
Contributor Author

sprider commented Aug 25, 2019

Thank you Jospeh @sprider ! Merged manually 🚀

Thank you for your guidance @VelinGeorgiev. I will implement the same in other teams report related commands.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants