最下面的问题。
说明:我们正在尝试自动化思科WebEx API的不同方面。例如,从API中获取所有设备和设备数据,然后显示它。这些设备可以显示连接状态、位置等等。这只是一个例子。
为了访问WebEx API,您需要执行以下操作:

然后输入您的密码:

在此之后,所有登录都将通过以下方式重定向:

登录后,可以使用文档并浏览API引用。在这里,您也可以尝试所有的功能,这是使用个人令牌,据我所知,不能导出或看到任何地方的网站。你可以复制并使用它,但它在24小时后过期。我想也许您可以使用Python登录您的帐户,并不断刷新您的个人令牌,但这似乎不是一个好的解决方案。

因此,我要谈一谈:

创建一个新应用程序,然后选择integration。



填写所有信息,然后单击“添加集成”。

正如您在黑匣子中看到的那样,在生成代码之前,需要将这个URL复制/粘贴到浏览器中,然后接受这些条款和条件。这是其结果:

复选框上写着:“只询问请求新权限的时间”,单击accept后,您将被重定向到创建应用程序集成时指定的URL。此网站不存在,但它仍将在URL中显示代码:

复制代码,现在可以使用应用程序中的以下代码和信息生成令牌集:
代码:
import requests, json
clientID = "C7aa20b0a57cae4127d1e08b15e3a94efacd5c7bb3e1a70ceed4308903a5b807b"
secretID = "b52db3ec6ad8622d0e0e01a0572bac982b214076308ea2e73a566fcf848c9369"
redirectURI = "https://www.your-oauth-website-here.dk/oauth"
def get_tokens(code):
"""Gets access token and refresh token"""
print("code:", code)
url = "https://api.ciscospark.com/v1/access_token"
headers = {'accept':'application/json','content-type':'application/x-www-form-urlencoded'}
payload = ("grant_type=authorization_code&client_id={0}&client_secret={1}&"
"code={2}&redirect_uri={3}").format(clientID, secretID, code, redirectURI)
req = requests.post(url=url, data=payload, headers=headers)
results = json.loads(req.text)
print(results)
access_token = results["access_token"]
refresh_token = results["refresh_token"]
return access_token, refresh_token
test = get_tokens("MWU4YTJmYTgtNjllMy00YjAzLTg0NTQtMTRkYTRiMmIxMzZkNWEzNzRkZDQtYTNk_PF84_33672567-1029-48fb-ba77-7fe2001ee897") # CODE结果:
code: MWU4YTJmYTgtNjllMy00YjAzLTg0NTQtMTRkYTRiMmIxMzZkNWEzNzRkZDQtYTNk_PF84_33672567-1029-48fb-ba77-7fe2001ee897
{'access_token': 'OTU5MWNhYTItOWNiZC00MWU1LThlZDktNjRlYjI5OGIyYjNmNjI2M2U2MzgtNjAz_PF84_33672567-1029-48fb-ba77-7fe2001ee897', 'expires_in': 1209599, 'refresh_token': 'MGQ4MWRmMzAtYjQyNi00Mzk1LWI0MzAtMmRkMGIzMWQ3ZDVjNzQwZDM3N2YtMWIw_PF84_33672567-1029-48fb-ba77-7fe2001ee897', 'refresh_token_expires_in': 7775999}如果尝试使用相同的代码生成新的令牌对,则会显示以下错误:
{'message': "POST failed: HTTP/1.1 400 Bad Request (url = https://idbroker.webex.com/idb/oauth2/v1/access_token, request/response TrackingId = ROUTER_5FD9B9DA-FCB3-01BB-03C9-503F01C403C9, error = '(invalid_grant) Authorization code has been used.')", 'errors': [{'description': "POST failed: HTTP/1.1 400 Bad Request (url = https://idbroker.webex.com/idb/oauth2/v1/access_token, request/response TrackingId = ROUTER_5FD9B9DA-FCB3-01BB-03C9-503F01C403C9, error = '(invalid_grant) Authorization code has been used.')"}], 'trackingId': 'ROUTER_5FD9B9DA-FCB3-01BB-03C9-503F01C403C9'}
Traceback (most recent call last):
File "c:/Python/test_shit.py", line 117, in <module>
test = get_tokens("MWU4YTJmYTgtNjllMy00YjAzLTg0NTQtMTRkYTRiMmIxMzZkNWEzNzRkZDQtYTNk_PF84_33672567-1029-48fb-ba77-7fe2001ee897") # CODE
File "c:/Python/test_shit.py", line 113, in get_tokens
access_token = results["access_token"]
KeyError: 'access_token'问题:令牌的有效性设置如下:
expiration.
在这段时间之后,您将必须经历创建新代码的过程,然后请求一组新的标记。
我很难了解如何在Red系统上使用Python2.7.5和CLI接口来自动化获取新代码的过程。
我尝试过使用请求库打开并单击accept,但没有取得任何成功。
下面是通过请求会话在黑匣子中打开代码URL时发生的情况的一个例子:
>>> url = "https://webexapis.com/v1/authorize?client_id=C7aa20b0a57cae4127d1e08b15e3a94efacd5c7bb3e1a70ceed4308903a5b807b&response_type=code&redirect_uri=https%3A%2F%2Fwww.your-oauth-website-here.dk%2Foauth&scope=spark%3Aall%20spark%3Akms&state=set_state_here"
>>> with requests.Session() as s:
... response = s.get(url)
...
>>> print(response.text)
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no" />
<title>
Sign In - Webex
</title>
<script src="https://code.jquery.com/jquery-3.5.1.min.js" integrity="sha256-9/aliU8dGd2tb6OSsuzixeV4y/faTqgFtohetphbbj0=" crossorigin="anonymous"></script>
<script>
window.jQuery || document.write("<script src='/idb/js/jquery-3.5.1.min.js'><\/script>");
</script>
<link rel="stylesheet" href="/idb/css/momentum-ui_fbdee616043ab213856f370993c83f01.min.css"/>
<link rel="stylesheet" href="/idb/css/idbstyle_service_default.css" type="text/css" />
<script src="/idb/js/auth_symphony_997017a549f50f21347311e1488607ab.js"></script>
<link rel="stylesheet" href="/idb/css/idbstyle_symphony_a2736f93e46b8c14f389ccac12436dcb.css" type="text/css" />
<link rel="apple-touch-icon" sizes="180x180" href="/idb/favicons/apple-touch-icon.png" />
<link rel="icon" type="image/png" sizes="32x32" href="/idb/favicons/favicon-32x32.png" />
<link rel="icon" type="image/png" sizes="16x16" href="/idb/favicons/favicon-16x16.png" />
<link rel="manifest" href="/idb/favicons/manifest.json" />
<link rel="mask-icon" href="/idb/favicons/safari-pinned-tab.svg" color="#07C1E4" />
<link rel="shortcut icon" href="/idb/favicons/favicon.ico" />
<meta name="msapplication-config" content="/idb/favicons/browserconfig.xml" />
<meta name="theme-color" content="#ffffff" />
<meta name="robots" content="noindex, nofollow" />
<!-- Ref: http://seclab.stanford.edu/websec/framebusting/framebust.pdf -->
<style id="antiClickjack">body{display:none !important;}</style>
<noscript><style>body{display:block !important;}</style></noscript>
<script type="text/javascript">
if (self === top) {
var antiClickjack = document.getElementById("antiClickjack");
antiClickjack.parentNode.removeChild(antiClickjack);
} else {
top.location = self.location;
}
</script>
<script>
var nameValidated = false;
var redirectUrl = "https://idbroker.webex.com/idb/IdBGlobalLogin?type=login&goto=https%3A%2F%2Fidbroker.webex.com%2Fidb%2Foauth2%2Fv1%2Fauthorize%3Fclient_id%3DC7aa20b0a57cae4127d1e08b15e3a94efacd5c7bb3e1a70ceed4308903a5b807b%26response_type%3Dcode%26redirect_uri%3Dhttps%253A%252F%252Fwww.your-oauth-website-here.dk%252Foauth%26scope%3Dspark%253Aall%2520spark%253Akms%26state%3Dset_state_here";
$(document).ready(function() {
$("#md-form").submit(function(e){
e.preventDefault();
if(nameValidated) {
processForm();
}
});
var cookieEmail = "";
if(cookieEmail.length > 0) {
$('#GlobalEmailLookupForm').find('input[id="email"]').val(cookieEmail);
$('#GlobalEmailLookupForm').find('input[id="isCookie"]').val("true");
$('#GlobalEmailLookupForm').submit();
}
});
function validateName(name, nameId) {
nameId = nameId.replace('IDToken' ,'');
var divId = 'DivToken' + nameId;
if(name.length > 0) {
$.ajax({
type: "POST",
url: "/idb/validateEmail",
data: { user: name, action: 'login', validate: "true" }
})
.done(function( responseData ) {
if(responseData.status == 'invalid') {
document.getElementById('nameContextualError'+nameId).innerHTML = "Enter a valid email address. Example: name@email.com"
highlightErrorInputTextbox(divId);
} else {
nameValidated = true;
}
});
}
}
function processForm() {
var email = $.trim(document.getElementById('IDToken1').value);
if(nameValidated) {
$('#GlobalEmailLookupForm').find('input[id="email"]').val(email);
$('#GlobalEmailLookupForm').submit();
} else {
if(email.length > 0) {
$.ajax({
type: "POST",
url: "/idb/validateEmail",
data: { user: email, action: 'login', validate: "true" }
})
.done(function( responseData ) {
if(responseData.status == 'invalid') {
document.getElementById('nameContextualError1').innerHTML = "Enter a valid email address. Example: name@email.com"
highlightErrorInputTextbox('DivToken1');
} else {
$('#GlobalEmailLookupForm').find('input[id="email"]').val(email);
$('#GlobalEmailLookupForm').submit();
}
});
}
}
return false;
}
</script>
<style>
@media (forced-colors: active) {
.md-button--blue {
border: 1px solid;
}
}
</style>
</head>
<body id="login" class="md md--sites">
<div id="globalInfo" style="display:none;">
<div>
It appears that cookies are not enabled on your computer, so some functions will not work. To enable cookies, change the privacy settings in your browser, and then refresh the page.
</div>
<a id="close_crossplatform_message" href="javascript:">
Close
</a>
</div>
<noscript>
<div>
It appears that JavaScript is not enabled on your computer, so some functions will not work. To enable JavaScript, change the privacy settings in your browser, and then refresh the page.
</div>
</noscript>
<div class="md-panel md-panel--form md-panel--full">
<div class="md-panel__main">
<div class="md-panel__image ci__logo"></div>
<div class="md-panel__title">
Enter your email address
</div>
<form class="md-panel__form" id="md-form" novalidate="">
<div class="md-input-container md-input--filled" id="DivToken1">
<div class="md-input__wrapper">
<input class="md-input" id="IDToken1" data-monitor-id="IDToken1"
name="IDToken1" value="" autocomplete="email"
placeholder="Email address"
alt="Email address"
onblur="validateName($.trim(this.value), this.id);" maxlength="512"
type="email" autofocus>
</div>
<div class="md-input__messages" id="DivErrorToken1">
<div class="message" id="nameContextualError1">
Enter the email address for your Webex account.
</div>
</div>
</div>
<div class="md-panel__cta">
<button name="btnOK" type="submit" id="IDButton2"
class="md-button md-button--blue" onClick="processForm();">
Next
</button>
</div>
</form>
</div>
<form name="GlobalEmailLookup" id="GlobalEmailLookupForm" method="post" action="/idb/globalLogin">
<input type="hidden" id="email" name="email" value="" />
<input type="hidden" id="isCookie" name="isCookie" value="false" />
<input type="hidden" id="ForceAuth" name="ForceAuth" value="false" />
<input type="hidden" id="cisService" name="cisService" value="common" />
<input type="hidden" name="gotoUrl" value="aHR0cHM6Ly9pZGJyb2tlci53ZWJleC5jb20vaWRiL29hdXRoMi92MS9hdXRob3JpemU/Y2xpZW50X2lkPUM3YWEyMGIwYTU3Y2FlNDEyN2QxZTA4YjE1ZTNhOTRlZmFjZDVjN2JiM2UxYTcwY2VlZDQzMDg5MDNhNWI4MDdiJnJlc3BvbnNlX3R5cGU9Y29kZSZyZWRpcmVjdF91cmk9aHR0cHMlM0ElMkYlMkZ3d3cueW91ci1vYXV0aC13ZWJzaXRlLWhlcmUuZGslMkZvYXV0aCZzY29wZT1zcGFyayUzQWFsbCUyMHNwYXJrJTNBa21zJnN0YXRlPXNldF9zdGF0ZV9oZXJl" />
<input type="hidden" id="encodedParamsString" name="encodedParamsString" value="dHlwZT1sb2dpbiY=" />
</form>
<div id="footer" class="md-panel__footer">
<img class="footer__logo" src="/idb/images/cisco-webex/lockup/cisco-webex-lockup-blue.svg" alt="Cisco Webex logo"/>
<div id="footer-links" class="footer__copyright">
By using Webex you accept the
<a href="https://www.cisco.com/c/en/us/about/legal/cloud-and-software/cloud-terms.html" target="_blank" rel="noopener">
Terms of Service
</a> &
<a href="https://www.cisco.com/web/siteassets/legal/privacy.html" target="_blank" rel="noopener">
Privacy Statement
</a>.
<a href="https://www.webex.com" target="_blank" rel="noopener">
Learn more about
</a> Webex
</div>
</div>
</div>
</body>
</html>我刚拿到登录屏幕。
或者:是否有一种方法可以使用Python登录WebEx网站?
如果我能登录到思科WebEx开发人员的网站,然后使用这个会话获得一个新的代码,这可能会成功。
更新:我已经设法通过了“输入电子邮件地址”,但我现在卡在输入密码,但我继续调查我如何可以登录到WebEx网站。
with requests.Session() as s:
login_url = "https://developer.webex.com/login"
result = s.get(login_url)
payload = { "email": "xx@xx.xx" }
print(result.url)
result = s.post(result.url, data=payload)
print(result.text)任何关于这件事的想法都将受到高度赞赏。
谢谢。
发布于 2020-12-17 09:53:05
结果发现,我没有正确地阅读文档,为那些花时间阅读/等等的人感到抱歉。
刷新令牌过期也将在刷新正常令牌时重置。我不知道是这样的,但是在今天联系了思科开发支持部门之后,他们向我展示了这一点。
官方答复如下:
嗨XXX,
感谢您联系Webex开发者支持。没有办法完全自动化OAuth授权流,因为第一步手动操作,用户授权集成代表他们行事始终是强制性的。但是,一旦访问令牌过期,甚至在此之前,您可以使用刷新令牌来扩展访问令牌的有效性。这样,刷新令牌的有效性也将被更新,因此实际上可以无限期地刷新您的访问令牌。由于性能原因,最多每天重置一次刷新令牌过期时间,因此计数器似乎在一天内开始计数,但是如果要在第二天刷新它,则应该会看到时间/整数恢复。
用于刷新令牌的代码:
def refreshCiscoWebExToken(refresh_token):
"""Refresh access token"""
payload = ( "grant_type=refresh_token&client_id={0}&client_secret={1}&"
"refresh_token={2}").format(clientID, secretID, refresh_token)
response = requests.post(url=TokenUrl, data=payload, headers=TokenHeaders)
if response.status_code == 200:
results = json.loads(response.text)
access_token = results["access_token"]
expires_in = results["expires_in"]
return(access_token, expires_in)我希望这能/将帮助其他人寻找答案。
https://stackoverflow.com/questions/65319807
复制相似问题