Skip to main content

Update Annotations

Changing annotation data is possible by PATCHing existing annotations. The application owner can change any user-created annotations. Collaborators are not allowed to change annotations made by other collaborators.

Generally speaking, you should send PATCH when you want to change the data you have posted; for example, changing the concept from positive to negative or adjusting the bounding box coordinates.

If you want to add more tags, you can always POST new annotations. There is no limit on how many annotations an input can have.

Update supports overwrite, merge, and remove actions. You can update from 1 up to 128 annotations in a single API call.

Update Annotation With Concepts

Below is an example of how to update an annotation of an image with a new concept, or change a concept value from true to false (or vice versa).

####################################################################################
# In this section, we set the user authentication, app ID, input ID, annotation ID,
# and concept ID. Change these strings to run your own example.
####################################################################################

USER_ID = 'YOUR_USER_ID_HERE'
# Your PAT (Personal Access Token) can be found in the Account's Security section
PAT = 'YOUR_PAT_HERE'
APP_ID = 'YOUR_APP_ID_HERE'
# Change these based on the annotation you want to update
INPUT_ID = '53d0362a9dfa4e03b2293375e2d0db73'
ANNOTATION_ID = '300b8e39a65e4f33ae4e15e86eaf4a3b'
CONCEPT_ID = 'apple'

##########################################################################
# YOU DO NOT NEED TO CHANGE ANYTHING BELOW THIS LINE TO RUN THIS EXAMPLE
##########################################################################

from clarifai_grpc.channel.clarifai_channel import ClarifaiChannel
from clarifai_grpc.grpc.api import resources_pb2, service_pb2, service_pb2_grpc
from clarifai_grpc.grpc.api.status import status_code_pb2

channel = ClarifaiChannel.get_grpc_channel()
stub = service_pb2_grpc.V2Stub(channel)

metadata = (('authorization', 'Key ' + PAT),)

userDataObject = resources_pb2.UserAppIDSet(user_id=USER_ID, app_id=APP_ID)

patch_annotations_response = stub.PatchAnnotations(
service_pb2.PatchAnnotationsRequest(
user_app_id=userDataObject, # The userDataObject is created in the overview and is required when using a PAT
action="merge", # Supported actions: overwrite, merge, remove.
annotations=[
resources_pb2.Annotation(
input_id=INPUT_ID,
id=ANNOTATION_ID,
data=resources_pb2.Data(
concepts=[
resources_pb2.Concept(id=CONCEPT_ID, value=1.) # 1 means true, this concept is present.
]
)
)
]
),
metadata=metadata
)

if patch_annotations_response.status.code != status_code_pb2.SUCCESS:
print(patch_annotations_response.status)
raise Exception("Patch annotations failed, status: " + patch_annotations_response.status.description)

Update Annotation With Concepts in a Region

When you update region data, you must nest this new data within region.data. Set the region_id to the current region_id if you do not want to change or remove this region.

Below is an example of how to update annotation with concepts in a region.

####################################################################################
# In this section, we set the user authentication, app ID, input ID, annotation ID,
# concept ID, and region ID. Change these strings to run your own example.
####################################################################################

USER_ID = 'YOUR_USER_ID_HERE'
# Your PAT (Personal Access Token) can be found in the Account's Security section
PAT = 'YOUR_PAT_HERE'
APP_ID = 'YOUR_APP_ID_HERE'
# Change these based on the annotation you want to update
INPUT_ID = '53d0362a9dfa4e03b2293375e2d0db73'
ANNOTATION_ID = '300b8e39a65e4f33ae4e15e86eaf4a3b'
CONCEPT_ID = 'tree'
REGION_ID = '361d6a9253be9152968012660258a4bf'

##########################################################################
# YOU DO NOT NEED TO CHANGE ANYTHING BELOW THIS LINE TO RUN THIS EXAMPLE
##########################################################################

from clarifai_grpc.channel.clarifai_channel import ClarifaiChannel
from clarifai_grpc.grpc.api import resources_pb2, service_pb2, service_pb2_grpc
from clarifai_grpc.grpc.api.status import status_code_pb2

channel = ClarifaiChannel.get_grpc_channel()
stub = service_pb2_grpc.V2Stub(channel)

metadata = (('authorization', 'Key ' + PAT),)

userDataObject = resources_pb2.UserAppIDSet(user_id=USER_ID, app_id=APP_ID)

patch_annotations_response = stub.PatchAnnotations(
service_pb2.PatchAnnotationsRequest(
user_app_id=userDataObject, # The userDataObject is created in the overview and is required when using a PAT
action="merge", # Supported actions: overwrite, merge, remove.
annotations=[
resources_pb2.Annotation(
input_id=INPUT_ID,
id=ANNOTATION_ID,
data=resources_pb2.Data(
regions=[
resources_pb2.Region(
id=REGION_ID, # this should be the region id of this annotation before patch
data=resources_pb2.Data(
concepts=[
resources_pb2.Concept(id=CONCEPT_ID, value=1.), # 1 means true, this concept is present.
]
)
)
]
)
)
]
),
metadata=metadata
)

if patch_annotations_response.status.code != status_code_pb2.SUCCESS:
print(patch_annotations_response.status)
raise Exception("Patch annotations failed, status: " + patch_annotations_response.status.description)

Update Annotation Region Coordinates

You can update region bounding boxes coordinates. When changing the region, you should use overwrite action. With overwrite action, you need to provide the data you want to keep in this annotation.

Below is an example of how to do that.

####################################################################################
# In this section, we set the user authentication, app ID, input ID, annotation ID,
# and concept ID. Change these strings to run your own example.
#####################################################################################

USER_ID = 'YOUR_USER_ID_HERE'
# Your PAT (Personal Access Token) can be found in the Account's Security section
PAT = 'YOUR_PAT_HERE'
APP_ID = 'YOUR_APP_ID_HERE'
# Change these based on the annotation you want to update
INPUT_ID = '53d0362a9dfa4e03b2293375e2d0db73'
ANNOTATION_ID = '300b8e39a65e4f33ae4e15e86eaf4a3b'
CONCEPT_ID = 'bike'

##########################################################################
# YOU DO NOT NEED TO CHANGE ANYTHING BELOW THIS LINE TO RUN THIS EXAMPLE
##########################################################################

from clarifai_grpc.channel.clarifai_channel import ClarifaiChannel
from clarifai_grpc.grpc.api import resources_pb2, service_pb2, service_pb2_grpc
from clarifai_grpc.grpc.api.status import status_code_pb2

channel = ClarifaiChannel.get_grpc_channel()
stub = service_pb2_grpc.V2Stub(channel)

metadata = (('authorization', 'Key ' + PAT),)

userDataObject = resources_pb2.UserAppIDSet(user_id=USER_ID, app_id=APP_ID)

patch_annotations_response = stub.PatchAnnotations(
service_pb2.PatchAnnotationsRequest(
user_app_id=userDataObject, # The userDataObject is created in the overview and is required when using a PAT
action="overwrite",
annotations=[
resources_pb2.Annotation(
input_id=INPUT_ID,
id=ANNOTATION_ID,
data=resources_pb2.Data(
regions=[
resources_pb2.Region(
region_info=resources_pb2.RegionInfo(
bounding_box=resources_pb2.BoundingBox( # move bounding box to new coordinates
top_row=0.5,
left_col=0.5,
bottom_row=0.8,
right_col=0.8
)
),
data=resources_pb2.Data( # need to provide tags you previously labeled since this is overwrite action
concepts=[
resources_pb2.Concept(id=CONCEPT_ID, value=1.), # 1 means true, this concept is present.
]
)
)
]
)
)
]
),
metadata=metadata
)

if patch_annotations_response.status.code != status_code_pb2.SUCCESS:
print(patch_annotations_response.status)
raise Exception("Patch annotations failed, status: " + patch_annotations_response.status.description)

Update Annotation Status

Below is an example of how to update an annotation status.

#############################################################################
# In this section, we set the user authentication, app ID, input ID, and
# annotation ID. Change these strings to run your own example.
#############################################################################

USER_ID = 'YOUR_USER_ID_HERE'
# Your PAT (Personal Access Token) can be found in the Account's Security section
PAT = 'YOUR_PAT_HERE'
APP_ID = 'YOUR_APP_ID_HERE'
# Change these based on the annotation status you want to update
INPUT_ID = 'c021c670357e4083b197abe80bda82b0'
ANNOTATION_ID = '8ac7fd96ce6f44b8a0f4806488b41b93'

##########################################################################
# YOU DO NOT NEED TO CHANGE ANYTHING BELOW THIS LINE TO RUN THIS EXAMPLE
##########################################################################

from clarifai_grpc.channel.clarifai_channel import ClarifaiChannel
from clarifai_grpc.grpc.api import resources_pb2, service_pb2, service_pb2_grpc
from clarifai_grpc.grpc.api.status import status_code_pb2, status_pb2

channel = ClarifaiChannel.get_grpc_channel()
stub = service_pb2_grpc.V2Stub(channel)

metadata = (('authorization', 'Key ' + PAT),)

userDataObject = resources_pb2.UserAppIDSet(user_id=USER_ID, app_id=APP_ID)

patch_annotations_response = stub.PatchAnnotations(
service_pb2.PatchAnnotationsRequest(
user_app_id=userDataObject, # The userDataObject is created in the overview and is required when using a PAT
action="merge", # Supported actions: overwrite, merge, remove.
annotations=[
resources_pb2.Annotation(
input_id=INPUT_ID,
id=ANNOTATION_ID,
status=status_pb2.Status(
code=status_code_pb2.ANNOTATION_SUCCESS
)
)
]
),
metadata=metadata
)

if patch_annotations_response.status.code != status_code_pb2.SUCCESS:
print(patch_annotations_response.status)
raise Exception("Patch annotations failed, status: " + patch_annotations_response.status.description)