Help, Draw with greace pencil from python

Hi everyone, I’m new to all of this, but what I want to do is draw a custom shape with grease pencil. After several experiments I was able to draw a line with this:

 def modal(self, context, event):

        bpy.ops.gpencil.draw(
        mode='DRAW', 
        stroke=[
        {"name":"", "location":(0, 0, 0), "mouse":(0,0), "mouse_event":(0,0), "pressure":1, "size":0, "pen_flip":False, "x_tilt":0, "y_tilt":0, "time":0, "is_start":True},
        {"name":"", "location":(0, 0, 0), "mouse":(550,150), "mouse_event":(0,0), "pressure":1, "size":0, "pen_flip":False, "x_tilt":0, "y_tilt":0, "time":0, "is_start":False}
        ], 
        wait_for_input=True, 
        disable_straight=False, 
        disable_fill=False, 
        guide_last_angle=0.0)
            

        if event.type in {'RIGHTMOUSE', 'ESC'}:
            return {'CANCELLED'}
        return {'RUNNING_MODAL'}

The result is several strokes that are continuously drawn on top of each other because the function is executed every time it receives an event.
My questions are: How is this function used?
Is it correct to execute it in the modal () function?
How can I draw, for example an ellipse, as I drag the mouse?
The idea is to create a custom tool similar to the circle tool in grease pencil.
I appreciate any help or tip to better understand all this.

Perhaps you would use the modal operator to draw the shape you want with BGL (or as widget) and then once you want to commit, send the data directly with the operator.

As for example on mouse press you draw with bgl, on mouse release you commit the data and clear them from list.

The reason is that the operator you want bpy.ops.gpencil.draw will always send data no matter what. However with BGL you can draw anything you want in the screen which is ideal for previews.

As for reference have a look at this:
blender\2.91\scripts\templates_py\operator_modal_draw.py