Open source the Sandbox plugin

Summary: This diff is mainly moving diffs around to open source the Sandbox plugin. I created the MD file writing some docs. The rest is just making our own FB implementation work

Reviewed By: danielbuechele

Differential Revision: D8731839

fbshipit-source-id: 27ac67223c6de9d1be406ab8c06b71b82d5407bc
This commit is contained in:
Edoardo Tognoni
2018-07-05 09:09:01 -07:00
committed by Facebook Github Bot
parent 03a8e696a9
commit 53753801b0
7 changed files with 276 additions and 1 deletions

View File

@@ -0,0 +1,71 @@
/*
* Copyright (c) 2004-present, Facebook, Inc.
*
* This source code is licensed under the MIT license found in the LICENSE
* file in the root directory of this source tree.
*
*/
package com.facebook.sonar.plugins.sandbox;
import com.facebook.sonar.core.SonarArray;
import com.facebook.sonar.core.SonarConnection;
import com.facebook.sonar.core.SonarObject;
import com.facebook.sonar.core.SonarPlugin;
import com.facebook.sonar.core.SonarReceiver;
import com.facebook.sonar.core.SonarResponder;
import java.util.Map;
public class SandboxSonarPlugin implements SonarPlugin {
public static final String ID = "Sandbox";
private static final String SET_METHOD_NAME = "setSandbox";
private static final String GET_METHOD_NAME = "getSandbox";
private final SandboxSonarPluginStrategy mStrategy;
public SandboxSonarPlugin(SandboxSonarPluginStrategy strategy) {
mStrategy = strategy;
}
@Override
public String getId() {
return ID;
}
@Override
public void onConnect(SonarConnection connection) {
connection.receive(
GET_METHOD_NAME,
new SonarReceiver() {
@Override
public void onReceive(SonarObject params, final SonarResponder responder) {
final SonarArray.Builder sandboxes = new SonarArray.Builder();
Map<String, String> knownSandboxes = mStrategy.getKnownSandboxes();
if (knownSandboxes == null) {
responder.success(sandboxes.build());
return;
}
for (String sandboxName : knownSandboxes.keySet()) {
sandboxes.put(
new SonarObject.Builder()
.put("name", sandboxName)
.put("value", knownSandboxes.get(sandboxName)));
}
responder.success(sandboxes.build());
}
});
connection.receive(
SET_METHOD_NAME,
new SonarReceiver() {
@Override
public void onReceive(SonarObject params, SonarResponder responder) throws Exception {
String sandbox = params.getString("sandbox");
mStrategy.setSandbox(sandbox);
responder.success(new SonarObject.Builder().put("result", true).build());
}
});
}
@Override
public void onDisconnect() {}
}

View File

@@ -0,0 +1,19 @@
/*
* Copyright (c) 2004-present, Facebook, Inc.
*
* This source code is licensed under the MIT license found in the LICENSE
* file in the root directory of this source tree.
*
*/
package com.facebook.sonar.plugins.sandbox;
import java.util.Map;
import javax.annotation.Nullable;
public interface SandboxSonarPluginStrategy {
@Nullable
Map<String, String> getKnownSandboxes();
void setSandbox(@Nullable String sandbox);
}

25
docs/sandbox-plugin.md Normal file
View File

@@ -0,0 +1,25 @@
---
id: sandbox-plugin
title: Sandbox
---
The Sandbox plugin is useful for developers that had to test changes of their apps by pointing them to some Sandbox environment. Through this plugin and a few lines of code in the client,
the app can get a callback and get the value that the user has input through Sonar. At this point, the developer can plugin its logic to save this setting in its app.
## Setup
To use the sandbox plugin, you need to add the plugin to your Sonar client instance.
### Android
```java
import com.facebook.sonar.plugins.SandboxSonarPlugin;
import com.facebook.sonar.plugins.SandboxSonarPluginStrategy;
final SandboxSonarPluginStrategy strategy = getStrategy(); // Your strategy goes here
client.addPlugin(new SandboxSonarPlugin(strategy));
```
### iOS
Coming soon

View File

@@ -0,0 +1,144 @@
/**
* Copyright 2018-present Facebook.
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
* @format
*/
import {SonarPlugin} from 'sonar';
import {FlexColumn} from 'sonar';
import {ButtonGroup, Button, styled, colors} from 'sonar';
export type Sandbox = {
name: string,
value: string,
};
type SandboxState = {|
sandboxes: Array<Sandbox>,
customSandbox: string,
showFeedback: boolean,
|};
const BigButton = Button.extends({
flexGrow: 1,
fontSize: 24,
padding: 20,
});
const ButtonContainer = FlexColumn.extends({
alignItems: 'center',
padding: 20,
});
export default class SandboxView extends SonarPlugin<SandboxState> {
state = {
sandboxes: [],
customSandbox: '',
showFeedback: false,
};
static title = 'Sandbox';
static id = 'Sandbox';
static icon = 'translate';
static TextInput = styled.textInput({
border: `1px solid ${colors.light10}`,
fontSize: '1em',
padding: '0 5px',
borderRight: 0,
borderTopLeftRadius: 4,
borderBottomLeftRadius: 4,
flexGrow: 1,
});
static FeedbackMessage = styled.text({
fontSize: '1.2em',
paddingTop: '10px',
color: 'green',
});
static TextInputLayout = FlexColumn.extends({
float: 'left',
justifyContent: 'center',
flexGrow: 1,
borderRadius: 4,
marginRight: 15,
marginTop: 15,
marginLeft: 15,
});
reducers = {
UpdateSandboxes(state: SandboxState, results: Object) {
return {
sandboxes: results.results,
};
},
};
init() {
this.client.call('getSandbox', {}).then((results: Array<Sandbox>) => {
this.dispatchAction({results, type: 'UpdateSandboxes'});
});
}
onSendSandboxEnvironment = (sandbox: string) => {
this.client
.call('setSandbox', {
sandbox: sandbox,
})
.then((result: Object) => {
setTimeout(() => {
this.setState({showFeedback: false});
}, 3000);
this.setState({showFeedback: result.result});
});
};
onChangeSandbox = (e: SyntheticInputEvent<>) => {
this.setState({customSandbox: e.target.value});
};
render() {
return (
<FlexColumn>
<SandboxView.TextInputLayout>
<ButtonGroup flexGrow={1}>
<SandboxView.TextInput
type="text"
placeholder="Sandbox URL (e.g. unixname.sb.facebook.com)"
key="sandbox-url"
onChange={this.onChangeSandbox}
onKeyPress={event => {
if (event.key === 'Enter') {
this.onSendSandboxEnvironment(this.state.customSandbox);
}
}}
/>
<Button
key="sandbox-send"
icon="download"
onClick={() =>
this.onSendSandboxEnvironment(this.state.customSandbox)
}
disabled={this.state.customSandbox == null}
/>
</ButtonGroup>
<SandboxView.FeedbackMessage
hidden={this.state.showFeedback == false}>
Success!
</SandboxView.FeedbackMessage>
</SandboxView.TextInputLayout>
{this.state.sandboxes.map(sandbox => (
<ButtonContainer>
<BigButton
key={sandbox.value}
onClick={() => this.onSendSandboxEnvironment(sandbox.value)}>
{sandbox.name}
</BigButton>
</ButtonContainer>
))}
</FlexColumn>
);
}
}

View File

@@ -0,0 +1,7 @@
{
"name": "sonar-plugin-sandbox",
"version": "1.0.0",
"main": "index.js",
"license": "MIT",
"gatekeeper": "sonar_sandbox_plugin"
}

View File

@@ -0,0 +1,4 @@
# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY.
# yarn lockfile v1

View File

@@ -1,7 +1,12 @@
{
"docs": {
"Using Sonar": ["getting-started", "understand", "stetho"],
"Built-in Plugins": ["logs-plugin", "layout-plugin", "network-plugin"],
"Built-in Plugins": [
"logs-plugin",
"layout-plugin",
"network-plugin",
"sandbox-plugin"
],
"Plugins: Desktop part": [
"js-setup",
"communicating",