New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Serenity/JS should provide the actual value of a note in reports #2223
Comments
Another consideration is the |
I like this idea, though. Some thoughts:
|
Also maybe it would be possible to consider mute or quiet notes, and by that i mean that all the note reports is its value. For the example above it would be:
This would allow to use notes for sharing test data |
this way masked values can be detected as a special case and we can avoid leaking secrets when producing a parameterised description of an activity Related tickets: re #2223
this way masked values can be detected as a special case and we can avoid leaking secrets when producing a parameterised description of an activity Related tickets: re #2223
…ptions of Activities `description` is a new tag function that interprets the provided template literal to generate a question which could be then used to describe any parameterised activities (tasks and interactions) Related tickets: re #2223
…sing Questions this allows the description to by determined dynamically when the activity is performed, and include the actual value of any Answerable parameters passed to the description in the test execution report Related tickets: re #2223
Hi @jan-molak, looks good. Just what to give some feedback: From my point of view, there is still some value to know that the text comes from a note in the report. Otherwise one can tend to search for a hard coded string in the specs. |
@viper3400 - good point. So are you thinking we should report both the name of the question and its value? For example:
Is that what you had in mind? I'm also wondering if Or maybe we should approach it differently altogether. Maybe we should have the description kept simple, e.g.:
and have a data attachment showing how the values were arrived at? 🤔
|
@jan-molak, I ment exactly what you've wrote first -> report both the name of the question and its value.
The data attachment would be an enhancement one can think about, but it will blow up the report as this would apply to each and every interaction that runs against a PageElement, right? I would start simple. :) |
I like your proposed format:
It will be interesting to see what it looks like with questions that have some transformations attached to them, like
and so on.. Maybe there's a way to make it look nicer.. 🤔 |
Would it be possible to use both kind of notes? Maybe it is different kind of notebook? One that gives text, other that does not. For sharing test data informing users that this is a note feels redundant. However the test data can be implemented with getters and then there is no need to complicate Serenity/JS implementation with it. Does setter of note changes to include the value? Given the user notes value of input as "price" |
I'm not sure if I follow, could you please give me an example of what you mean by getters? |
actually i didnt test it... 🤔 as per discussion in gitter chat
doesnt work as the globalVariable was modified after its value was retrieved. i assume that if globalVariable would be a function it would work as the function would be resolved on execution... ⬇️i have different sets of test data, some of which is fixed, some is changed during execution as per example. Current file structure is something like this:
I reference this file in my imports and modify as desired, "Before" steps cleans the dynamic data
i invented this test case to demonstrate following challenges: (1.) and (2.) doesnt work as per original question in chat. maybe if my dataSet file had functions instead:
then i could write
and maybe this would bypass the case, but i just split the actor action to 2 instead of trying it (3.) and (4.) another attempt to work with data that is defined in step. I found myself doing 4. a lot when the data interactions are needed. "note of quantity" is not what i need for action, i just need its value in test case as well as report.
Hence the request 🙃 |
That's fine, Let's say the structure of our custom notepad looks as follows: interface MyNotes {
country: string;
currency: string;
vat: number;
//placeholders for dynamic data modified during execution (usually Given steps)
itemId: string;
} And the task to manipulate items in the basket is defined like this (I like your DSL, by the way 👍): import { Answerable, Task, d } from '@serenity-js/core';
class Basket {
static add = (quantity: Answerable<number>) => ({
items: (name: Answerable<string) =>
Task.where(d`#actor adds ${ quantity } ${ name } to the basket`,
// .. add the item
notes<MyNotes>().set('itemId', LastResponse.body<{ itemId: string }>().itemId)
)
})
} The result of calling You can now retrieve it by calling await actor.attemptsTo(
Enter.theValue(notes<MyNotes>().get('itemId')).into(field)
) If you want to pass it to another task, you'll need to define its parameter as const myTask = (noteId: Answerable<string>) =>
Task.where(`#actor ...`,
Enter.theValue(noteId).into(field)
)
await actor.attemptsTo(
myTask(notes<MyNotes>().get('itemId'))
) Adding asynchronous valuesPerforming arithmetic operations on values retrieved from const a = Promise.resolve(1)
const b = Promise.resolve(3)
console.log(a + b)
// prints: `[object Promise][object Promise]`. That's not what we're after. You need to either resolve the values before performing the operation: const a = await Promise.resolve(1)
const b = await Promise.resolve(3)
console.log(a + b)
// prints: 4 or you need to chain the operations: const a = Promise.resolve(1)
const b = Promise.resolve(3)
a.then(valueOfA => b.then(valueOfB => valueOfA + valueOfB)).then(console.log)
// pritns: 4 The same applies to questions: const a = Question.about('value of a', actor => 1)
const b = Question.about('value of b', actor => 3)
console.log(a + b)
// prints: `value of avalue of b`. That's not what we're after, either. Here again, you can resolve the values before performing the operations: const a = Question.about('value of a', actor => 1)
const b = Question.about('value of b', actor => 3)
const valueOfA = await actor.answer(a)
const valueOfB = await actor.answer(b)
console.log(a + b)
// prints: 4 Or you can chain the operations by creating a "higher-order" question: const sumOf = (first: Answerable<number>, second: Answerable<number>) =>
Question.about(d`sum of ${ first } and ${ second }`, async actor => {
const valueOfA = await actor.answer(a)
const valueOfB = await actor.answer(b)
return valueOfA + valueOfB
})
await actor.attemptsTo(
Enter.theValue(sumOf(notes<MyNotes>().get('quantity'), quantity)).into(field)
) Alternatively, if the second addend is a static value, you can also look at the operation as a mapping function: const a = Question.about('value of a', actor => 1)
const b = 3
const increasedBy = (value: number) =>
(input: number) =>
input + value;
const result = await actor.answer(
a.as(increasedBy(b)
)
console.log(result)
// prints: 4 And so: await actor.attemptsTo(
Enter.theValue(
notes<MyNotes>().get('quantity')
.as(increasedBy(quantity))
).into(field)
) Hope this helps! |
Thanks! It is clear. |
What's the problem you're trying to solve?
When dealing with
notes
reporting just contain the name of the note, but not the actual value of the note.user ensures that the text of Answer field ('My answer') does equal a note of answer ('My answer')
How would you like to solve it?
Challenge: Reporting interactions when values are unknown at the start.
Issue: Error messages contain values if an interaction fails, but values are unresolved initially.
Solution for Post-Run Reporters:
Challenge with Real-Time Console Reporter:
Proposed Solution:
Consideration for HTML Reports:
Extension Idea:
notes().get('recordedItems').andShowTheValueInReports()
.Edge Case Discussion Needed:
Are there any alternatives?
No response
How can we make it happen?
The text was updated successfully, but these errors were encountered: