UDF can not handle None?

udf
python

#1

Hello.

I tried to use UDF with Python Client.

And I found a weird situation.

I put data with None value. And I fetched data with query and UDF.

as_client = aerospike.client(AS_CONFIG).connect()

as_bins = { "name": "Yunseop", "phone": None }

as_client.remove(('test', 'test_none', 1))
as_client.put(('test', 'test_none', 1), as_bins)

query = as_client.query('test', 'test_none')
as_records1 = query.results()

print as_records1
# [(('test', 'test_none', 1, bytearray(b'\x0f\x94D\xe3~\xdb\xb3\xf3\xe9\xc6\xe7p\xdf\xf1\xc1l\x1eR^\xe3')), {'gen': 1, 'ttl': 432000}, {'phone': None, 'name': 'Yunseop'})]
as_client.udf_put('./just_udf.lua')

query = as_client.query('test', 'test_none')
query.apply('just_udf', 'test', [])
as_records2 = query.results()
print as_records2
# [{'phone': bytearray(b'N.'), 'name': 'Yunseop'}]

just_udf.lua is

local function map_profile(record)
  return map {phone=record.phone, name=record.name}
end

function test(stream) 
  return stream : map(map_profile)
end

Why returned bytearray(b'N.') instead of None when using UDF??


#2

Use aerospike.null() instead of None when setting the bin value to None.

{"phone":aerospike.null()}

See code example at: https://www.aerospike.com/apidocs/python/client.html?highlight=bin#aerospike.Client.put

BTW, you don’t have to remove the key before the put. By default put will update it. Setting a bin to null will delete the bin from the record.


#3

That is strange. Thank you for that simple test case that reproduces the issue. Could you share what version of the Python client, and what version of the server you are using?

bytearray(b'N.') is the actual content of what is getting stored into the database by the Python client.

None does not map to a native Aerospike type, so it is serialized using Pickle. The Pickle serialization of None looks like 'N.' , the Python client takes that value and stores it as bytes of type AS_BYTES_PYTHON into the Aerospike database.

When you retrieve it with aerospike.get the value is deserialized so you end up getting None back. So it looks like the deserialization isn’t being run on this returned value when it is coming back from an aggregation uff for some reason.

I’ll look into it and see if I can figure out what is going on.


#4

Thanks.

I used Python client aerospike==2.2.3 and Aerospike Community Edition - 4.0.13


#5

CE 4.0.13? How did you install this version?


#6

@pgupta Sorry. My mistake

I use Aerospike Community Edition 3.14.1.2


#7

Python documentation says use aerospike.null() - you are not in UDF at this line.