I am using two actions of IBM cloud function - write1 and write2 (both using PYTHON).
I created a sequence that should pass value from write1 to write2.
I wrote a PYTHON code in write1 action but is throws some JSON error.
Write 1 Python File:*
import os
import sys
import json
import requests
import ibm_boto3
from ibm_botocore.client import Config, ClientError
cos = ibm_boto3.resource("s3",
ibm_api_key_id='my-api-key',
ibm_service_instance_id='my-instance-id',
config=Config(signature_version="oauth"),
endpoint_url='https://s3.eu-gb.cloud-object-storage.appdomain.cloud'
)
def get_item(bucket_name, item_name):
a={"Retrieving item from bucket":bucket_name , "key": item_name}
print(json.dumps(a))
try:
file = cos.Object(bucket_name, item_name).get()
return file["Body"].read()
except ClientError as be:
w={"CLIENT ERROR":be}
print(json.dumps(w))
except Exception as e:
y={"Unable to retrieve file contents":e}
print(json.dumps(y))
def test():
x = get_item('cloud-college-bucket0','abc.txt')
print(x.decode('utf-8'))
if x is not None:
string_in_uppercase = x.upper();
n={"String in Uppercase =":string_in_uppercase.decode('utf-8')}
b=json.dumps(n)
print(b)
def main(dict):
return test()
if __name__ == '__main__':
main()
Error it throws:
Results:
{
"error": "**The action did not produce a valid JSON response**: null\n"
}
Logs:
[
"2019-10-08T13:01:56.339677Z stderr: /usr/local/lib/python3.7/site-packages/ibm_botocore/vendored/requests/api.py:67: DeprecationWarning: You are using the post() function from 'ibm_botocore.vendored.requests'. This is not a public API in ibm_botocore and will be removed in the future. Additionally, this version of requests is out of date. We recommend you install the requests package, 'import requests' directly, and use the requests.post() function instead.",
"2019-10-08T13:01:56.339748Z stderr: DeprecationWarning",
"2019-10-08T13:01:56.339755Z stderr: /usr/local/lib/python3.7/site-packages/ibm_botocore/vendored/requests/models.py:169: DeprecationWarning:
Using or importing the ABCs from 'collections' instead of from 'collections.abc' is deprecated, and in 3.8 it will stop working",
"2019-10-08T13:01:56.339759Z stderr: if isinstance(hook, collections.Callable):",
"2019-10-08T13:01:56.339678Z stdout: {\"Retrieving item from bucket\": \"cloud-college-bucket0\", \"key\": \"abc.txt\"}",
"2019-10-08T13:01:56.339772Z stdout: hello friends",
"2019-10-08T13:01:56.339776Z stdout: {\"String in Uppercase =\": \"HELLO FRIENDS\"}",
"2019-10-08T13:01:56.340Z stderr: The action did not initialize or run as expected. Log data might be missing."
]
It says import request which I did but still the problem persists.
I also say use request.post function but how and where to use is what I am unable to understand. And how to solve this JSON issue?
And the desired output is shown in the logs.
From the first outset, I could see that the test function only prints the JSON but never returns it. But you if you see the sample Python action, it always should return a JSON
import sys
def main(dict):
return { 'message': 'Hello world' }
Also, you can check the supported packages list with Python runtime here before using them in your action.
If you have a package that is not in the list, you can always package Python code with a virtual environment in .zip files or Packaging code in Docker images
Related
I am trying to implement hostname like module and my target machine in an amazon-ec2. But When I am running the script its giving me below error:
[ansible-user#ansible-master ~]$ ansible node1 -m edit_hostname.py -a node2
ERROR! this task 'edit_hostname.py' has extra params, which is only allowed in the following modules: meta, group_by, add_host, include_tasks, import_role, raw, set_fact, command, win_shell, import_tasks, script, shell, include_vars, include_role, include, win_command
My module is like this:
#!/usr/bin/python
from ansible.module_utils.basic import *
try:
import json
except ImportError:
import simplejson as json
def write_to_file(module, hostname, hostname_file):
try:
with open(hostname_file, 'w+') as f:
try:
f.write("%s\n" %hostname)
finally:
f.close()
except Exception:
err = get_exception()
module.fail_json(msg="failed to write to the /etc/hostname file")
def main():
hostname_file = '/etc/hostname'
module = AnsibleModule(argument_spec=dict(name=dict(required=True, type=str)))
name = module.params['name']
write_to _file(module, name, hostname_file)
module.exit_json(changed=True, meta=name)
if __name__ == "__main__":
main()
I don't know where I am making the mistake. Any help will be greatly appreciated. Thank you.
When developing a new module, I would recommend to use the boilerplate described in the documentation. This also shows that you'll need to use AnsibleModule to define your arguments.
In your main, you should add something like the following:
def main():
# define available arguments/parameters a user can pass to the module
module_args = dict(
name=dict(type='str', required=True)
)
# seed the result dict in the object
# we primarily care about changed and state
# change is if this module effectively modified the target
# state will include any data that you want your module to pass back
# for consumption, for example, in a subsequent task
result = dict(
changed=False,
original_hostname='',
hostname=''
)
module = AnsibleModule(
argument_spec=module_args
supports_check_mode=False
)
# manipulate or modify the state as needed (this is going to be the
# part where your module will do what it needs to do)
result['original_hostname'] = module.params['name']
result['hostname'] = 'goodbye'
# use whatever logic you need to determine whether or not this module
# made any modifications to your target
result['changed'] = True
# in the event of a successful module execution, you will want to
# simple AnsibleModule.exit_json(), passing the key/value results
module.exit_json(**result)
Then, you can call the module like so:
ansible node1 -m mymodule.py -a "name=myname"
ERROR! this task 'edit_hostname.py' has extra params, which is only allowed in the following modules: meta, group_by, add_host, include_tasks, import_role, raw, set_fact, command, win_shell, import_tasks, script, shell, include_vars, include_role, include, win_command
As explained by your error message, an anonymous default parameter is only supported by a limited number of modules. In your custom module, the paramter you created is called name. Moreover, you should not include the .py extension in the module name. You have to call your module like so as an ad-hoc command:
$ ansible node1 -m edit_hostname -a name=node2
I did not test your module code so you may have further errors to fix.
Meanwhile, I still strongly suggest you use the default boilerplate from the ansible documentation as proposed in #Simon's answer.
I have a simple Python Code that uses Elasticsearch module "curator" to make snapshots.
I've tested my code locally and it works.
Now I want to run it in an AWS Lambda but I have this error :
Unable to import module 'lambda_function': No module named 'error'
Here is how I proceeded :
I created manually a Lambda and gave it a "AISA-BasicLambdaExecutionRole" role. Then I created my package with my function and the dependencies that I installed with the command :
pip install elasticsearch-curator -t /<path>/myRepository
I zipped the content (not the folder) and uploaded it in my Lambda.
I changed the Handler name to "lambda_function.lambda_handler" (my function's name is "lambda_function.py").
Did I miss something ? This is my first time working with Lambda and Python
I've seen the other questions about this error :
"errorMessage": "Unable to import module 'lambda_function'"
But nothing works for me.
EDIT :
Here is my lambda_function :
from __future__ import print_function
import curator
import time
from curator.exceptions import NoIndices
from elasticsearch import Elasticsearch
def lambda_handler(event, context):
es = Elasticsearch()
index_list = curator.IndexList(es)
index_list.filter_by_regex(kind='prefix', value="logstash-")
Number = 1
try:
while Number <= 3:
Name="snapshotLmbd_n_"+ str(Number) +""
curator.Snapshot(index_list, repository="s3-backup", name= Name , wait_for_completion=True).do_action()
Number += 1
print('Just taking a nap ! will be back soon')
time.sleep(30)
except KeyboardInterrupt:
print('My bad ! I interrupted this')
return
Thank you for your time.
Ok, since you have everything else correct, check for the permissions of the python script.
It must have executable permissions (755)
I'm new to Python. This is my first Ansible module in order to delete the SimpleDB domain from ChaosMonkey deletion.
When tested in my local venv with my Mac OS X, it keeps saying
Module unable to decode valid JSON on stdin. Unable to figure out
what parameters were passed.
Here is the code:
#!/usr/bin/python
# Delete SimpleDB Domain
from ansible.module_utils.basic import *
import boto3
def delete_sdb_domain():
fields = dict(
sdb_domain_name=dict(required=True, type='str')
)
module = AnsibleModule(argument_spec=fields)
client = boto3.client('sdb')
response = client.delete_domain(DomainName='module.params['sdb_domain_name']')
module.exit_json(changed = False, meta = response)
def main():
delete_sdb_domain()
if __name__ == '__main__':
main()
And I'm trying to pass in parameters from this file: /tmp/args.json.
and run the following command to make the local test:
$ python ./delete_sdb_domain.py /tmp/args.json
please note I'm using venv test environment on my Mac.
If you find any syntax error in my module, please also point it out.
This is not how you should test your modules.
AnsibleModule expects to have specific JSON as stdin data.
So the closest thing you can try is:
python ./delete_sdb_domain.py < /tmp/args.json
But I bet you have your json file in wrong format (no ANSIBLE_MODULE_ARGS, etc.).
To debug your modules you can use test-module script from Ansible hacking pack:
./hacking/test-module -m delete_sdb_domain.py -a "sdb_domain_name=zzz"
I am trying to write a Volatility plugin to extract configuration file used by a malware from memory dump. However, when I run this plugin (without 'sudo') without root privileges the plugin crashes at the line yara.compile. If I run this plugin with 'sudo', code after yara.compile line is not getting executed. I am not sure why yara.compile is causing this problem. Could someone help me with this? Following is the code I have written:
import volatility.plugins.common as common
import volatility.utils as utils
import volatility.win32.tasks as tasks
import volatility.debug as debug
import volatility.plugins.malware.malfind as malfind
import volatility.conf as conf
import volatility.plugins.taskmods as taskmods
try:
import yara
HAS_YARA = True
except ImportError:
HAS_YARA = False
YARA_SIGS = {
'malware_conf' : 'rule malware_conf {strings: $a = /<settings/ condition: $a}'
}
class malwarescan(taskmods.PSList):
def get_vad_base(self, task, address):
for vad in task.VadRoot.traverse():
if address >= vad.Start and address < vad.End:
return vad.Start
return None
def calculate(self):
if not HAS_YARA:
debug.error('Yara must be installed for this plugin')
print "in calculate function"
kernel_space = utils.load_as(self._config)
print "before yara compile"
rules = yara.compile(sources=YARA_SIGS)
print "after yara compile"
for process in tasks.pslist(kernel_space):
if "IEXPLORE.EXE".lower() == process.ImageFileName.lower():
scanner = malfind.VadYaraScanner(task=process, rules=rules)
for hit, address in scanner.scan():
vad_base_addr = self.get_vad_base(process, address)
yield process, address
def render_text(self, outfd, data):
for process, address in data:
outfd.write("Process: {0}, Pid: {1}\n".format(process.ImageFileName, process.UniqueProcessId))
So when I run this plugin with root privilege, I dont see the line "print 'after yara compile'" gets executed. What could be the reason? Thank you.
I installed "yara" through "pip". If you install yara through pip, you actually get yara-ctypes (https://github.com/mjdorma/yara-ctypes) which is a bit different than yara-python. So I uninstalled yara-ctypes and installed yara-python. Then it worked.
I have the following python script which runs perfectly if run separately:
import arcpy
val = arcpy.GetCellValue_management("D:\dem-merged\lidar_wsg84", "-95.090174910630012 29.973962146120652", "")
print str(val)
I want to expose this as a web service and so I installed web.py and wrote the following code for code.py. but it gives errors(when invoked. compiles fine).
import web
import arcpy
urls = (
'/(.*)', 'hello'
)
app = web.application(urls, globals())
class hello:
def GET(self, name):
val = arcpy.GetCellValue_management("D:\dem-merged\lidar_wsg84", "-95.090174910630012 29.973962146120652", "")
return str(val)
if __name__ == "__main__":
app.run()
When i invoke this using http://localhost:8080, i get the following error:
<class 'arcgisscripting.ExecuteError'> at /
ERROR 000582: Error occurred during execution.
Python C:\Program Files (x86)\ArcGIS\Desktop10.0\arcpy\arcpy\management.py in GetCellValue, line 8460
Web GET http://localhost:8080/
Traceback (innermost first)
C:\Program Files (x86)\ArcGIS\Desktop10.0\arcpy\arcpy\management.py in GetCellValue
be returned."""
try:
retval = convertArcObjectToPythonObject(gp.GetCellValue_management(*gp_fixargs((in_raster, location_point, band_index), True)))
return retval
except Exception, e:
raise e ...
#gptooldoc('GetRasterProperties_management', None)
def GetRasterProperties(in_raster=None, property_type=None):
"""GetRasterProperties_management(in_raster, {property_type})
Returns the properties of a raster dataset.
I have tried Debugging it in many ways, the code .py runs fine if i just return a "hello". The library i am using is a ArcGIS Geoprocessing toolbox library.
Any ideas as to what might be wrong?
That looks like an error from the third party module. Try finding out what that error code (000582) actually means to the application.