mirror of
https://github.com/Grasscutters/mitmproxy.git
synced 2024-11-26 18:18:25 +00:00
Merge pull request #1190 from mitmproxy/file_menu_save_open
File menu save open
This commit is contained in:
commit
65fde7f554
@ -8,6 +8,8 @@ import re
|
|||||||
|
|
||||||
import six
|
import six
|
||||||
import tornado.websocket
|
import tornado.websocket
|
||||||
|
from io import BytesIO
|
||||||
|
from mitmproxy.flow import FlowWriter, FlowReader
|
||||||
|
|
||||||
from mitmproxy import filt
|
from mitmproxy import filt
|
||||||
from mitmproxy import version
|
from mitmproxy import version
|
||||||
@ -159,6 +161,26 @@ class Flows(RequestHandler):
|
|||||||
data=[_strip_content(f.get_state()) for f in self.state.flows]
|
data=[_strip_content(f.get_state()) for f in self.state.flows]
|
||||||
))
|
))
|
||||||
|
|
||||||
|
class DumpFlows(RequestHandler):
|
||||||
|
def get(self):
|
||||||
|
self.set_header("Content-Disposition", "attachment; filename=flows")
|
||||||
|
self.set_header("Content-Type", "application/octet-stream")
|
||||||
|
|
||||||
|
bio = BytesIO()
|
||||||
|
fw = FlowWriter(bio)
|
||||||
|
for f in self.state.flows:
|
||||||
|
fw.add(f)
|
||||||
|
|
||||||
|
self.write(bio.getvalue())
|
||||||
|
bio.close()
|
||||||
|
|
||||||
|
def post(self):
|
||||||
|
self.state.clear()
|
||||||
|
|
||||||
|
content = self.request.files.values()[0][0]["body"]
|
||||||
|
bio = BytesIO(content)
|
||||||
|
self.state.load_flows(FlowReader(bio).stream())
|
||||||
|
bio.close()
|
||||||
|
|
||||||
class ClearAll(RequestHandler):
|
class ClearAll(RequestHandler):
|
||||||
|
|
||||||
@ -356,6 +378,7 @@ class Application(tornado.web.Application):
|
|||||||
(r"/updates", ClientConnection),
|
(r"/updates", ClientConnection),
|
||||||
(r"/events", Events),
|
(r"/events", Events),
|
||||||
(r"/flows", Flows),
|
(r"/flows", Flows),
|
||||||
|
(r"/flows/dump", DumpFlows),
|
||||||
(r"/flows/accept", AcceptFlows),
|
(r"/flows/accept", AcceptFlows),
|
||||||
(r"/flows/(?P<flow_id>[0-9a-f\-]+)", FlowHandler),
|
(r"/flows/(?P<flow_id>[0-9a-f\-]+)", FlowHandler),
|
||||||
(r"/flows/(?P<flow_id>[0-9a-f\-]+)/accept", AcceptFlow),
|
(r"/flows/(?P<flow_id>[0-9a-f\-]+)/accept", AcceptFlow),
|
||||||
|
@ -310,12 +310,10 @@ var _jquery = require("jquery");
|
|||||||
|
|
||||||
var _jquery2 = _interopRequireDefault(_jquery);
|
var _jquery2 = _interopRequireDefault(_jquery);
|
||||||
|
|
||||||
var _lodash = require("lodash");
|
|
||||||
|
|
||||||
var _lodash2 = _interopRequireDefault(_lodash);
|
|
||||||
|
|
||||||
var _dispatcher = require("./dispatcher.js");
|
var _dispatcher = require("./dispatcher.js");
|
||||||
|
|
||||||
|
var _utils = require("./utils.js");
|
||||||
|
|
||||||
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
||||||
|
|
||||||
var ActionTypes = exports.ActionTypes = {
|
var ActionTypes = exports.ActionTypes = {
|
||||||
@ -433,6 +431,18 @@ var FlowActions = exports.FlowActions = {
|
|||||||
},
|
},
|
||||||
clear: function clear() {
|
clear: function clear() {
|
||||||
_jquery2.default.post("/clear");
|
_jquery2.default.post("/clear");
|
||||||
|
},
|
||||||
|
download: function download() {
|
||||||
|
return window.location = "/flows/dump";
|
||||||
|
},
|
||||||
|
|
||||||
|
upload: function upload(file) {
|
||||||
|
var data = new FormData();
|
||||||
|
data.append('file', file);
|
||||||
|
(0, _utils.fetchApi)("/flows/dump", {
|
||||||
|
method: 'post',
|
||||||
|
body: data
|
||||||
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -442,7 +452,7 @@ var Query = exports.Query = {
|
|||||||
SHOW_EVENTLOG: "e"
|
SHOW_EVENTLOG: "e"
|
||||||
};
|
};
|
||||||
|
|
||||||
},{"./dispatcher.js":22,"jquery":"jquery","lodash":"lodash"}],3:[function(require,module,exports){
|
},{"./dispatcher.js":22,"./utils.js":27,"jquery":"jquery"}],3:[function(require,module,exports){
|
||||||
"use strict";
|
"use strict";
|
||||||
|
|
||||||
var _react = require("react");
|
var _react = require("react");
|
||||||
@ -3513,18 +3523,27 @@ var FileMenu = _react2.default.createClass({
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
handleOpenClick: function handleOpenClick(e) {
|
handleOpenClick: function handleOpenClick(e) {
|
||||||
|
this.fileInput.click();
|
||||||
|
e.preventDefault();
|
||||||
|
},
|
||||||
|
handleOpenFile: function handleOpenFile(e) {
|
||||||
|
if (e.target.files.length > 0) {
|
||||||
|
_actions.FlowActions.upload(e.target.files[0]);
|
||||||
|
this.fileInput.value = "";
|
||||||
|
}
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
console.error("unimplemented: handleOpenClick");
|
|
||||||
},
|
},
|
||||||
handleSaveClick: function handleSaveClick(e) {
|
handleSaveClick: function handleSaveClick(e) {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
console.error("unimplemented: handleSaveClick");
|
_actions.FlowActions.download();
|
||||||
},
|
},
|
||||||
handleShutdownClick: function handleShutdownClick(e) {
|
handleShutdownClick: function handleShutdownClick(e) {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
console.error("unimplemented: handleShutdownClick");
|
console.error("unimplemented: handleShutdownClick");
|
||||||
},
|
},
|
||||||
render: function render() {
|
render: function render() {
|
||||||
|
var _this = this;
|
||||||
|
|
||||||
var fileMenuClass = "dropdown pull-left" + (this.state.showFileMenu ? " open" : "");
|
var fileMenuClass = "dropdown pull-left" + (this.state.showFileMenu ? " open" : "");
|
||||||
|
|
||||||
return _react2.default.createElement(
|
return _react2.default.createElement(
|
||||||
@ -3548,6 +3567,29 @@ var FileMenu = _react2.default.createClass({
|
|||||||
"New"
|
"New"
|
||||||
)
|
)
|
||||||
),
|
),
|
||||||
|
_react2.default.createElement(
|
||||||
|
"li",
|
||||||
|
null,
|
||||||
|
_react2.default.createElement(
|
||||||
|
"a",
|
||||||
|
{ href: "#", onClick: this.handleOpenClick },
|
||||||
|
_react2.default.createElement("i", { className: "fa fa-fw fa-folder-open" }),
|
||||||
|
"Open..."
|
||||||
|
),
|
||||||
|
_react2.default.createElement("input", { ref: function ref(_ref) {
|
||||||
|
return _this.fileInput = _ref;
|
||||||
|
}, className: "hidden", type: "file", onChange: this.handleOpenFile })
|
||||||
|
),
|
||||||
|
_react2.default.createElement(
|
||||||
|
"li",
|
||||||
|
null,
|
||||||
|
_react2.default.createElement(
|
||||||
|
"a",
|
||||||
|
{ href: "#", onClick: this.handleSaveClick },
|
||||||
|
_react2.default.createElement("i", { className: "fa fa-fw fa-floppy-o" }),
|
||||||
|
"Save..."
|
||||||
|
)
|
||||||
|
),
|
||||||
_react2.default.createElement("li", { role: "presentation", className: "divider" }),
|
_react2.default.createElement("li", { role: "presentation", className: "divider" }),
|
||||||
_react2.default.createElement(
|
_react2.default.createElement(
|
||||||
"li",
|
"li",
|
||||||
@ -6602,7 +6644,7 @@ _lodash2.default.extend(LiveStoreMixin.prototype, {
|
|||||||
this._fetchxhr = _jquery2.default.getJSON("/" + this.type).done(function (message) {
|
this._fetchxhr = _jquery2.default.getJSON("/" + this.type).done(function (message) {
|
||||||
this.handle_fetch(message.data);
|
this.handle_fetch(message.data);
|
||||||
}.bind(this)).fail(function () {
|
}.bind(this)).fail(function () {
|
||||||
EventLogActions.add_event("Could not fetch " + this.type);
|
_actions.EventLogActions.add_event("Could not fetch " + this.type);
|
||||||
}.bind(this));
|
}.bind(this));
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@ -6792,7 +6834,11 @@ Object.defineProperty(exports, "__esModule", {
|
|||||||
value: true
|
value: true
|
||||||
});
|
});
|
||||||
exports.formatTimeStamp = exports.formatTimeDelta = exports.formatSize = exports.Key = undefined;
|
exports.formatTimeStamp = exports.formatTimeDelta = exports.formatSize = exports.Key = undefined;
|
||||||
|
|
||||||
|
var _extends = Object.assign || function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; };
|
||||||
|
|
||||||
exports.reverseString = reverseString;
|
exports.reverseString = reverseString;
|
||||||
|
exports.fetchApi = fetchApi;
|
||||||
|
|
||||||
var _jquery = require("jquery");
|
var _jquery = require("jquery");
|
||||||
|
|
||||||
@ -6877,7 +6923,7 @@ function getCookie(name) {
|
|||||||
var r = document.cookie.match(new RegExp("\\b" + name + "=([^;]*)\\b"));
|
var r = document.cookie.match(new RegExp("\\b" + name + "=([^;]*)\\b"));
|
||||||
return r ? r[1] : undefined;
|
return r ? r[1] : undefined;
|
||||||
}
|
}
|
||||||
var xsrf = _jquery2.default.param({ _xsrf: getCookie("_xsrf") });
|
var xsrf = "_xsrf=" + getCookie("_xsrf");
|
||||||
|
|
||||||
//Tornado XSRF Protection.
|
//Tornado XSRF Protection.
|
||||||
_jquery2.default.ajaxPrefilter(function (options) {
|
_jquery2.default.ajaxPrefilter(function (options) {
|
||||||
@ -6900,6 +6946,17 @@ _jquery2.default.ajaxPrefilter(function (options) {
|
|||||||
alert(message);
|
alert(message);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
function fetchApi(url, options) {
|
||||||
|
if (url.indexOf("?") === -1) {
|
||||||
|
url += "?" + xsrf;
|
||||||
|
} else {
|
||||||
|
url += "&" + xsrf;
|
||||||
|
}
|
||||||
|
return fetch(url, _extends({}, options, {
|
||||||
|
credentials: 'same-origin'
|
||||||
|
}));
|
||||||
|
}
|
||||||
|
|
||||||
},{"./actions.js":2,"jquery":"jquery","lodash":"lodash","react":"react"}]},{},[3])
|
},{"./actions.js":2,"jquery":"jquery","lodash":"lodash","react":"react"}]},{},[3])
|
||||||
|
|
||||||
|
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -1,6 +1,6 @@
|
|||||||
import $ from "jquery";
|
import $ from "jquery";
|
||||||
import _ from "lodash";
|
|
||||||
import {AppDispatcher} from "./dispatcher.js";
|
import {AppDispatcher} from "./dispatcher.js";
|
||||||
|
import {fetchApi} from "./utils.js";
|
||||||
|
|
||||||
export var ActionTypes = {
|
export var ActionTypes = {
|
||||||
// Connection
|
// Connection
|
||||||
@ -117,6 +117,16 @@ export var FlowActions = {
|
|||||||
},
|
},
|
||||||
clear: function(){
|
clear: function(){
|
||||||
$.post("/clear");
|
$.post("/clear");
|
||||||
|
},
|
||||||
|
download: () => window.location = "/flows/dump",
|
||||||
|
|
||||||
|
upload: (file) => {
|
||||||
|
let data = new FormData();
|
||||||
|
data.append('file', file);
|
||||||
|
fetchApi("/flows/dump", {
|
||||||
|
method: 'post',
|
||||||
|
body: data
|
||||||
|
})
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -344,12 +344,19 @@ var FileMenu = React.createClass({
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
handleOpenClick: function (e) {
|
handleOpenClick: function (e) {
|
||||||
|
this.fileInput.click();
|
||||||
|
e.preventDefault();
|
||||||
|
},
|
||||||
|
handleOpenFile: function (e) {
|
||||||
|
if (e.target.files.length > 0) {
|
||||||
|
FlowActions.upload(e.target.files[0]);
|
||||||
|
this.fileInput.value = "";
|
||||||
|
}
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
console.error("unimplemented: handleOpenClick");
|
|
||||||
},
|
},
|
||||||
handleSaveClick: function (e) {
|
handleSaveClick: function (e) {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
console.error("unimplemented: handleSaveClick");
|
FlowActions.download();
|
||||||
},
|
},
|
||||||
handleShutdownClick: function (e) {
|
handleShutdownClick: function (e) {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
@ -368,6 +375,20 @@ var FileMenu = React.createClass({
|
|||||||
New
|
New
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
|
<li>
|
||||||
|
<a href="#" onClick={this.handleOpenClick}>
|
||||||
|
<i className="fa fa-fw fa-folder-open"></i>
|
||||||
|
Open...
|
||||||
|
</a>
|
||||||
|
<input ref={(ref) => this.fileInput = ref} className="hidden" type="file" onChange={this.handleOpenFile}/>
|
||||||
|
|
||||||
|
</li>
|
||||||
|
<li>
|
||||||
|
<a href="#" onClick={this.handleSaveClick}>
|
||||||
|
<i className="fa fa-fw fa-floppy-o"></i>
|
||||||
|
Save...
|
||||||
|
</a>
|
||||||
|
</li>
|
||||||
<li role="presentation" className="divider"></li>
|
<li role="presentation" className="divider"></li>
|
||||||
<li>
|
<li>
|
||||||
<a href="http://mitm.it/" target="_blank">
|
<a href="http://mitm.it/" target="_blank">
|
||||||
@ -376,18 +397,6 @@ var FileMenu = React.createClass({
|
|||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
{/*
|
{/*
|
||||||
<li>
|
|
||||||
<a href="#" onClick={this.handleOpenClick}>
|
|
||||||
<i className="fa fa-fw fa-folder-open"></i>
|
|
||||||
Open
|
|
||||||
</a>
|
|
||||||
</li>
|
|
||||||
<li>
|
|
||||||
<a href="#" onClick={this.handleSaveClick}>
|
|
||||||
<i className="fa fa-fw fa-save"></i>
|
|
||||||
Save
|
|
||||||
</a>
|
|
||||||
</li>
|
|
||||||
<li role="presentation" className="divider"></li>
|
<li role="presentation" className="divider"></li>
|
||||||
<li>
|
<li>
|
||||||
<a href="#" onClick={this.handleShutdownClick}>
|
<a href="#" onClick={this.handleShutdownClick}>
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
import _ from "lodash";
|
import _ from "lodash";
|
||||||
import $ from "jquery";
|
import $ from "jquery";
|
||||||
import {EventEmitter} from 'events';
|
import {EventEmitter} from 'events';
|
||||||
|
import { EventLogActions } from "../actions.js"
|
||||||
import {ActionTypes, StoreCmds} from "../actions.js";
|
import {ActionTypes, StoreCmds} from "../actions.js";
|
||||||
import {AppDispatcher} from "../dispatcher.js";
|
import {AppDispatcher} from "../dispatcher.js";
|
||||||
|
|
||||||
|
@ -80,7 +80,7 @@ function getCookie(name) {
|
|||||||
var r = document.cookie.match(new RegExp("\\b" + name + "=([^;]*)\\b"));
|
var r = document.cookie.match(new RegExp("\\b" + name + "=([^;]*)\\b"));
|
||||||
return r ? r[1] : undefined;
|
return r ? r[1] : undefined;
|
||||||
}
|
}
|
||||||
var xsrf = $.param({_xsrf: getCookie("_xsrf")});
|
const xsrf = `_xsrf=${getCookie("_xsrf")}`;
|
||||||
|
|
||||||
//Tornado XSRF Protection.
|
//Tornado XSRF Protection.
|
||||||
$.ajaxPrefilter(function (options) {
|
$.ajaxPrefilter(function (options) {
|
||||||
@ -101,4 +101,16 @@ $(document).ajaxError(function (event, jqXHR, ajaxSettings, thrownError) {
|
|||||||
console.error(thrownError, message, arguments);
|
console.error(thrownError, message, arguments);
|
||||||
actions.EventLogActions.add_event(thrownError + ": " + message);
|
actions.EventLogActions.add_event(thrownError + ": " + message);
|
||||||
alert(message);
|
alert(message);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
export function fetchApi(url, options) {
|
||||||
|
if(url.indexOf("?") === -1){
|
||||||
|
url += "?" + xsrf;
|
||||||
|
} else {
|
||||||
|
url += "&" + xsrf;
|
||||||
|
}
|
||||||
|
return fetch(url, {
|
||||||
|
...options,
|
||||||
|
credentials: 'same-origin'
|
||||||
|
});
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user