Adding model update, model migrator, curved line support, relationship lines, remove of web-services classes
This commit is contained in:
@@ -417,7 +417,7 @@
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<!-- <plugin>
|
||||
<groupId>org.codehaus.mojo</groupId>
|
||||
<artifactId>jaxws-maven-plugin</artifactId>
|
||||
<executions>
|
||||
@@ -439,7 +439,7 @@
|
||||
</wsdlFiles>
|
||||
</configuration>
|
||||
</plugin>
|
||||
|
||||
-->
|
||||
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
|
@@ -83,7 +83,7 @@ public final class Mailer {
|
||||
}
|
||||
};
|
||||
|
||||
this.mailSender.send(preparator);
|
||||
//this.mailSender.send(preparator);
|
||||
}
|
||||
|
||||
public void setMailSender(JavaMailSender mailer) {
|
||||
|
@@ -1,22 +1,22 @@
|
||||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You under the Apache License, Version 2.0
|
||||
* (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* $Id: file 64488 2006-03-10 17:32:09Z paulo $
|
||||
*/
|
||||
|
||||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You under the Apache License, Version 2.0
|
||||
* (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* $Id: file 64488 2006-03-10 17:32:09Z paulo $
|
||||
*/
|
||||
|
||||
package com.wisemapping.service;
|
||||
|
||||
import com.wisemapping.dao.UserManager;
|
||||
@@ -24,6 +24,7 @@ import com.wisemapping.exceptions.WiseMappingException;
|
||||
import com.wisemapping.mail.Mailer;
|
||||
import com.wisemapping.model.User;
|
||||
import com.wisemapping.model.Colaborator;
|
||||
import org.apache.log4j.Logger;
|
||||
|
||||
import java.util.Calendar;
|
||||
import java.util.HashMap;
|
||||
@@ -35,6 +36,7 @@ public class UserServiceImpl
|
||||
private UserManager userManager;
|
||||
private MindmapService mindmapService;
|
||||
private Mailer mailer;
|
||||
final static Logger logger = Logger.getLogger("org.wisemapping.service");
|
||||
|
||||
public void activateAcount(long code)
|
||||
throws InvalidActivationCodeException
|
||||
@@ -113,6 +115,7 @@ public class UserServiceImpl
|
||||
model.put("user", user);
|
||||
// TODO: ver como no hacer hardcode el url
|
||||
final String activationUrl = "http://wisemapping.com/c/activation.htm?code=" + user.getActivationCode();
|
||||
logger.info("create User - acrivationUrl: "+activationUrl);
|
||||
model.put("emailcheck", activationUrl);
|
||||
mailer.sendEmail(mailer.getRegistrationEmail(), user.getEmail(), "Welcome to Wisemapping!", model,
|
||||
"confirmationMail.vm");
|
||||
|
@@ -1,160 +0,0 @@
|
||||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You under the Apache License, Version 2.0
|
||||
* (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* $Id: file 64488 2006-03-10 17:32:09Z paulo $
|
||||
*/
|
||||
|
||||
package com.wisemapping.ws;
|
||||
|
||||
import org.springframework.ws.server.endpoint.annotation.Endpoint;
|
||||
import org.springframework.ws.server.endpoint.annotation.PayloadRoot;
|
||||
import org.apache.log4j.Logger;
|
||||
import com.wisemapping.service.MindmapService;
|
||||
import com.wisemapping.service.UserService;
|
||||
import com.wisemapping.model.MindMap;
|
||||
import com.wisemapping.model.User;
|
||||
import com.wisemapping.exceptions.NoMapFoundException;
|
||||
|
||||
import javax.xml.bind.*;
|
||||
import javax.xml.transform.stream.StreamSource;
|
||||
import java.io.StringReader;
|
||||
import java.io.StringWriter;
|
||||
import java.util.Calendar;
|
||||
|
||||
/**
|
||||
* WiseMapping Web Services API
|
||||
*/
|
||||
@Endpoint
|
||||
public class WiseWsEndpoint {
|
||||
|
||||
MindmapService mindmapService;
|
||||
private UserService userService;
|
||||
final static Logger logger = Logger.getLogger("org.wisemapping.ws");
|
||||
private JAXBContext jaxbContext;
|
||||
|
||||
|
||||
public WiseWsEndpoint(MindmapService mindmapService, UserService userService) throws JAXBException {
|
||||
this.mindmapService = mindmapService;
|
||||
this.userService = userService;
|
||||
jaxbContext = JAXBContext.newInstance("com.wisemapping.ws");
|
||||
}
|
||||
|
||||
@PayloadRoot(localPart = "loadMindmapRequest", namespace = "http://www.wisemapping.org/ws")
|
||||
public LoadMindmapResponse loadMindmap(final LoadMindmapRequest request) throws Throwable {
|
||||
|
||||
logger.debug("Invoking loadMindmap");
|
||||
final LoadMindmapResponse result = new LoadMindmapResponse();
|
||||
|
||||
try {
|
||||
final MindMap mindmap = mindmapService.getMindmapById((int) request.getMapdId());
|
||||
if(mindmap==null)
|
||||
{
|
||||
throw new NoMapFoundException(request.getMapdId());
|
||||
}
|
||||
|
||||
String xml = mindmap.getNativeXml();
|
||||
|
||||
// Hack, we need to unify to only one XSD schema definitions per map ...
|
||||
xml = "<map xmlns=\"http://www.wisemapping.org/mindmap\"" + xml.substring(4,xml.length());
|
||||
|
||||
Unmarshaller unmarshaller = jaxbContext.createUnmarshaller();
|
||||
|
||||
final StringReader stringReader = new StringReader(xml);
|
||||
final StreamSource streamSource = new StreamSource(stringReader);
|
||||
final JAXBElement<MapType> mapElement = unmarshaller.unmarshal(streamSource,MapType.class);
|
||||
|
||||
// Load map data ...
|
||||
result.creator = mindmap.getCreator();
|
||||
result.setMap(mapElement.getValue());
|
||||
} catch (Throwable e) {
|
||||
logger.fatal("Unexpexted Exception", e);
|
||||
throw e;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
@PayloadRoot(localPart = "addMindmapRequest", namespace = "http://www.wisemapping.org/ws")
|
||||
public AddMindmapResponse createMindmap(final AddMindmapRequest request) throws Throwable {
|
||||
|
||||
logger.debug("Invoking createMindmap");
|
||||
final AddMindmapResponse response = new AddMindmapResponse();
|
||||
try {
|
||||
|
||||
final String creator = request.getCreator();
|
||||
final User user = userService.getUserBy(creator);
|
||||
if(user==null)
|
||||
{
|
||||
throw new IllegalArgumentException("Invalid addMindmapRequest.' " + creator+"' is not valid wisemapping user.");
|
||||
}
|
||||
|
||||
|
||||
final MindMap mindmap = new MindMap();
|
||||
mindmap.setCreationTime(Calendar.getInstance());
|
||||
|
||||
// Set title ...
|
||||
final String title = request.getTitle();
|
||||
if(title==null)
|
||||
{
|
||||
throw new IllegalArgumentException("Invalid addMindmapRequest. Title element can not be null.");
|
||||
}
|
||||
mindmap.setTitle(title);
|
||||
|
||||
// Set description ...
|
||||
final String description = request.getDescription();
|
||||
if(description==null)
|
||||
{
|
||||
throw new IllegalArgumentException("Invalid addMindmapRequest. Description element can not be null.");
|
||||
}
|
||||
mindmap.setDescription(description);
|
||||
|
||||
// Convert Map to XML
|
||||
final MapType mapType = request.getMap();
|
||||
if(mapType==null)
|
||||
{
|
||||
throw new IllegalArgumentException("Invalid addMindmapRequest. Map element can not be null.");
|
||||
}
|
||||
|
||||
ObjectFactory factory = new ObjectFactory();
|
||||
final Marshaller marshaller = jaxbContext.createMarshaller();
|
||||
StringWriter stringWriter = new StringWriter();
|
||||
marshaller.marshal(factory.createMap(mapType),stringWriter);
|
||||
|
||||
mindmap.setNativeXml(stringWriter.toString());
|
||||
mindmapService.addMindmap(mindmap,user);
|
||||
|
||||
|
||||
// Prepare result ...
|
||||
response.setMapId(mindmap.getId());
|
||||
|
||||
} catch (Throwable e) {
|
||||
logger.fatal("Unexpexted Exception", e);
|
||||
throw e;
|
||||
|
||||
}
|
||||
|
||||
return response;
|
||||
}
|
||||
|
||||
|
||||
public MindmapService getMindmapService() {
|
||||
return mindmapService;
|
||||
}
|
||||
|
||||
public void setMindmapService(MindmapService mindmapService) {
|
||||
this.mindmapService = mindmapService;
|
||||
}
|
||||
}
|
@@ -10,11 +10,12 @@
|
||||
<xsd:complexType name="mapType">
|
||||
<xsd:sequence>
|
||||
<xsd:element ref="topic" minOccurs="1" maxOccurs='unbounded'/>
|
||||
<xsd:element ref="relationship" minOccurs="0" maxOccurs='unbounded'/>
|
||||
</xsd:sequence>
|
||||
<xsd:attribute name="name" type="xsd:string"/>
|
||||
<xsd:attribute name="version" type="xsd:string"/>
|
||||
</xsd:complexType>
|
||||
|
||||
|
||||
<xsd:element name="topic" type="topicType"/>
|
||||
|
||||
<xsd:complexType name="topicType">
|
||||
@@ -32,6 +33,7 @@
|
||||
<xsd:attribute name="order" type="xsd:int"/>
|
||||
<xsd:attribute name="position" type="xsd:string"/>
|
||||
<xsd:attribute name="central" type="xsd:boolean"/>
|
||||
<xsd:attribute name="id" type="xsd:ID" use="optional"/>
|
||||
</xsd:complexType>
|
||||
|
||||
<xsd:complexType name="icon">
|
||||
@@ -48,4 +50,15 @@
|
||||
<xsd:attribute name="text" type="xsd:string"/>
|
||||
</xsd:complexType>
|
||||
|
||||
<xsd:element name="relationship" type="relationshipType"/>
|
||||
<xsd:complexType name="relationshipType">
|
||||
<xsd:attribute name="id" type="xsd:ID"/>
|
||||
<xsd:attribute name="srcTopicId" type="xsd:ID"/>
|
||||
<xsd:attribute name="destTopicId" type="xsd:ID"/>
|
||||
<xsd:attribute name="lineType" type="xsd:string"/>
|
||||
<xsd:attribute name="srcCtrlPoint" type="xsd:string"/>
|
||||
<xsd:attribute name="destCtrlPoint" type="xsd:string"/>
|
||||
<xsd:attribute name="endArrow" type="xsd:boolean"/>
|
||||
</xsd:complexType>
|
||||
|
||||
</xsd:schema>
|
@@ -216,11 +216,11 @@ div#node {
|
||||
}
|
||||
|
||||
div#font {
|
||||
left: 619px; /*left:581px;*/
|
||||
left: 656px; /*left:581px;*/
|
||||
}
|
||||
|
||||
div#share {
|
||||
left: 815px; /*left:777px;*/
|
||||
left: 852px; /*left:777px;*/
|
||||
}
|
||||
|
||||
div#saveButton {
|
||||
@@ -311,6 +311,12 @@ div#topicLink {
|
||||
z-index: 4;
|
||||
}
|
||||
|
||||
div#topicRelation {
|
||||
background: url(../images/topic_link.png) no-repeat center top;
|
||||
behavior: url(../css/iepngfix.htc);
|
||||
z-index: 4;
|
||||
}
|
||||
|
||||
div#topicNote {
|
||||
background-image: url(../images/note.png);
|
||||
behavior: url(../css/iepngfix.htc);
|
||||
|
@@ -269,7 +269,7 @@ function afterMindpotLibraryLoading()
|
||||
designer.deleteCurrentNode();
|
||||
});
|
||||
var context = this;
|
||||
var colorPicker1 = new MooRainbow('topicColor', {
|
||||
/*var colorPicker1 = new MooRainbow('topicColor', {
|
||||
id: 'topicColor',
|
||||
imgPath: '../images/',
|
||||
startColor: [255, 255, 255],
|
||||
@@ -298,12 +298,16 @@ function afterMindpotLibraryLoading()
|
||||
onComplete: function(color) {
|
||||
removeCurrentColorPicker.attempt(colorPicker2, context);
|
||||
}
|
||||
});
|
||||
});*/
|
||||
$('topicLink').addEvent('click', function(event) {
|
||||
designer.addLink2SelectedNode();
|
||||
|
||||
});
|
||||
|
||||
$('topicRelation').addEvent('click', function(event) {
|
||||
designer.addRelationShip2SelectedNode(event);
|
||||
});
|
||||
|
||||
$('topicNote').addEvent('click', function(event) {
|
||||
designer.addNote2SelectedNode();
|
||||
|
||||
@@ -318,7 +322,7 @@ function afterMindpotLibraryLoading()
|
||||
designer.setStyle2SelectedNode();
|
||||
});
|
||||
|
||||
var colorPicker3 = new MooRainbow('fontColor', {
|
||||
/*var colorPicker3 = new MooRainbow('fontColor', {
|
||||
id: 'fontColor',
|
||||
imgPath: '../images/',
|
||||
startColor: [255, 255, 255],
|
||||
@@ -332,7 +336,7 @@ function afterMindpotLibraryLoading()
|
||||
onComplete: function(color) {
|
||||
removeCurrentColorPicker.attempt(colorPicker3, context);
|
||||
}
|
||||
});
|
||||
});*/
|
||||
|
||||
// Save event handler ....
|
||||
var saveButton = $('saveButton');
|
||||
@@ -520,7 +524,6 @@ function buildMindmapDesigner()
|
||||
var container = $('mindplot');
|
||||
|
||||
// Initialize Editor ...
|
||||
var persistantManager = new mindplot.PersistanceManager(window.MapEditorService);
|
||||
|
||||
var screenWidth = window.getWidth();
|
||||
var screenHeight = window.getHeight();
|
||||
@@ -533,7 +536,7 @@ function buildMindmapDesigner()
|
||||
editorProperties.width = screenWidth;
|
||||
editorProperties.height = screenHeight;
|
||||
|
||||
designer = new mindplot.MindmapDesigner(editorProperties, container, persistantManager);
|
||||
designer = new mindplot.MindmapDesigner(editorProperties, container);
|
||||
designer.loadFromXML(mapId, mapXml);
|
||||
|
||||
// If a node has focus, focus can be move to another node using the keys.
|
||||
|
@@ -67,7 +67,6 @@ function buildMindmapDesigner()
|
||||
var container = $('mindplot');
|
||||
|
||||
// Initialize Editor ...
|
||||
var persistantManager = new mindplot.PersistanceManager(window.MapEditorService);
|
||||
|
||||
var screenWidth = window.getWidth();
|
||||
var screenHeight = window.getHeight();
|
||||
@@ -77,7 +76,7 @@ function buildMindmapDesigner()
|
||||
editorProperties.height = screenHeight;
|
||||
editorProperties.viewMode = true;
|
||||
|
||||
designer = new mindplot.MindmapDesigner(editorProperties, container, persistantManager);
|
||||
designer = new mindplot.MindmapDesigner(editorProperties, container);
|
||||
designer.loadFromXML(mapId, mapXml);
|
||||
|
||||
// If a node has focus, focus can be move to another node using the keys.
|
||||
|
@@ -15,9 +15,10 @@
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
<%--
|
||||
<script src="http://www.google-analytics.com/urchin.js" type="text/javascript">
|
||||
</script>
|
||||
<script type="text/javascript">
|
||||
_uacct = "UA-2347723-1";
|
||||
urchinTracker();
|
||||
</script>
|
||||
</script>--%>
|
||||
|
@@ -1,3 +1,4 @@
|
||||
<%@page pageEncoding="UTF-8"%>
|
||||
<%@ taglib prefix="c" uri="http://java.sun.com/jstl/core_rt" %>
|
||||
<%@ taglib prefix="spring" uri="http://www.springframework.org/tags" %>
|
||||
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form" %>
|
||||
|
@@ -192,6 +192,9 @@
|
||||
<div id="topicLink" class="button" title="<spring:message code="TOPIC_LINK"/>">
|
||||
<div class="toolbarLabel"><p><spring:message code="LINK"/></p></div>
|
||||
</div>
|
||||
<div id="topicRelation" class="button" title="<spring:message code="TOPIC_RELATIONSHIP"/>">
|
||||
<div class="toolbarLabel"><p><spring:message code="TOPIC_RELATIONSHIP"/></p></div>
|
||||
</div>
|
||||
</fieldset>
|
||||
</div>
|
||||
<div id="font" class="buttonContainer" title="Font Properties">
|
||||
@@ -332,11 +335,11 @@
|
||||
<script type="text/javascript" src="../dwr/interface/MapEditorService.js"></script>
|
||||
</c:if>
|
||||
<script type="text/javascript" src="../js/editor.js"></script>
|
||||
<script src="http://www.google-analytics.com/urchin.js" type="text/javascript">
|
||||
<%--<script src="http://www.google-analytics.com/urchin.js" type="text/javascript">
|
||||
</script>
|
||||
<script type="text/javascript">
|
||||
_uacct = "UA-2347723-1";
|
||||
urchinTracker();
|
||||
</script>
|
||||
</script>--%>
|
||||
</body>
|
||||
</html>
|
||||
|
@@ -1,4 +1,5 @@
|
||||
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
|
||||
<%@page pageEncoding="UTF-8"%>
|
||||
<%@ taglib prefix="tiles" uri="http://struts.apache.org/tags-tiles" %>
|
||||
<%@ include file="/jsp/init.jsp" %>
|
||||
|
||||
|
@@ -1,100 +0,0 @@
|
||||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You under the Apache License, Version 2.0
|
||||
* (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* $Id: file 64488 2006-03-10 17:32:09Z paulo $
|
||||
*/
|
||||
|
||||
package com.wisemapping.ws.test;
|
||||
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
import javax.xml.bind.JAXBContext;
|
||||
import javax.xml.bind.JAXBException;
|
||||
import javax.xml.bind.Marshaller;
|
||||
import java.net.MalformedURLException;
|
||||
import java.io.StringWriter;
|
||||
import java.util.List;
|
||||
|
||||
import com.wisemapping.ws.*;
|
||||
|
||||
|
||||
@Test(groups = {"wsintegration"})
|
||||
public class WiseWebServicesTest {
|
||||
|
||||
|
||||
@Test(dependsOnMethods = "addMapTest")
|
||||
public void loadMapTest() throws MalformedURLException, JAXBException {
|
||||
|
||||
final WiseServicesPortTypeService portTypeService = new WiseServicesPortTypeService();
|
||||
final WiseServicesPortType servicesPortType = portTypeService.getWiseServicesPortTypeSoap11();
|
||||
|
||||
final LoadMindmapRequest request = new LoadMindmapRequest();
|
||||
request.setMapdId(1);
|
||||
LoadMindmapResponse response = servicesPortType.loadMindmap(request);
|
||||
|
||||
JAXBContext jc = JAXBContext.newInstance("com.wisemapping.ws.test");
|
||||
Marshaller marshaller = jc.createMarshaller();
|
||||
|
||||
final StringWriter xmlContext = new StringWriter();
|
||||
marshaller.marshal(response,xmlContext);
|
||||
System.out.println("Response:"+xmlContext);
|
||||
|
||||
}
|
||||
|
||||
public void addMapTest() throws MalformedURLException, JAXBException {
|
||||
|
||||
final WiseServicesPortTypeService portTypeService = new WiseServicesPortTypeService();
|
||||
final WiseServicesPortType servicesPortType = portTypeService.getWiseServicesPortTypeSoap11();
|
||||
|
||||
final AddMindmapRequest request = new AddMindmapRequest();
|
||||
|
||||
request.setCreator("test@wisemapping.org");
|
||||
|
||||
request.setTitle("MyFirstMap");
|
||||
request.setDescription("My First Map Description");
|
||||
|
||||
// Set Map ...
|
||||
MapType sampleMap = createMockMap();
|
||||
request.setMap(sampleMap);
|
||||
|
||||
|
||||
AddMindmapResponse response = servicesPortType.addMindmap(request);
|
||||
|
||||
JAXBContext jc = JAXBContext.newInstance("com.wisemapping.ws.test");
|
||||
Marshaller marshaller = jc.createMarshaller();
|
||||
|
||||
final StringWriter xmlContext = new StringWriter();
|
||||
marshaller.marshal(response,xmlContext);
|
||||
System.out.println("Response:"+xmlContext);
|
||||
|
||||
}
|
||||
|
||||
private MapType createMockMap() {
|
||||
ObjectFactory factory = new ObjectFactory();
|
||||
MapType mapType = factory.createMapType();
|
||||
mapType.setName("map name");
|
||||
|
||||
TopicType topicType = factory.createTopicType();
|
||||
topicType.setCentral(true);
|
||||
topicType.setText("Central topic value");
|
||||
|
||||
List<TopicType> topics = mapType.getTopic();
|
||||
topics.add(topicType);
|
||||
|
||||
return mapType;
|
||||
}
|
||||
|
||||
}
|
Reference in New Issue
Block a user