/* (non-Javadoc) * @see com.mvplite.view.NavigationController#setStartView(com.mvplite.view.NavigateableView) */ @Override public void setStartView(NavigateableView view) { HistoryEntry entry = new HistoryEntry(); entry.eventsToFire = calculateEventsToFireList(view); historyStack.put("", entry); }
/** * Get the history after a specified revision. * * <p>The default implementation first fetches the full history and then throws away the oldest * revisions. This is not efficient, so subclasses should override it in order to get good * performance. Once every subclass has implemented a more efficient method, the default * implementation should be removed and made abstract. * * @param file the file to get the history for * @param sinceRevision the revision right before the first one to return, or {@code null} to * return the full history * @return partial history for file * @throws HistoryException on error accessing the history */ History getHistory(File file, String sinceRevision) throws HistoryException { // If we want an incremental history update and get here, warn that // it may be slow. if (sinceRevision != null) { Logger logger = OpenGrokLogger.getLogger(); logger.log( Level.WARNING, "Incremental history retrieval is not implemented for {0}.", getClass().getSimpleName()); logger.log(Level.WARNING, "Falling back to slower full history retrieval."); } History history = getHistory(file); if (sinceRevision == null) { return history; } List<HistoryEntry> partial = new ArrayList<>(); for (HistoryEntry entry : history.getHistoryEntries()) { partial.add(entry); if (sinceRevision.equals(entry.getRevision())) { // Found revision right before the first one to return. break; } } removeAndVerifyOldestChangeset(partial, sinceRevision); history.setHistoryEntries(partial); return history; }
/** * Get a map from author names to their ids in the database. The authors that are not in the * database are added to it. * * @param conn the connection to the database * @param history the history to get the author names from * @param reposId the id of the repository * @return a map from author names to author ids */ private Map<String, Integer> getAuthors(ConnectionResource conn, History history, int reposId) throws SQLException { HashMap<String, Integer> map = new HashMap<String, Integer>(); PreparedStatement ps = conn.getStatement(GET_AUTHORS); ps.setInt(1, reposId); try (ResultSet rs = ps.executeQuery()) { while (rs.next()) { map.put(rs.getString(1), rs.getInt(2)); } } PreparedStatement insert = conn.getStatement(ADD_AUTHOR); insert.setInt(1, reposId); for (HistoryEntry entry : history.getHistoryEntries()) { String author = entry.getAuthor(); if (!map.containsKey(author)) { int id = nextAuthorId.getAndIncrement(); insert.setString(2, author); insert.setInt(3, id); insert.executeUpdate(); map.put(author, id); conn.commit(); } } return map; }
/** * Update the history store with the value of an an read, write or execute operation. Also, the * timestamp of the insertion is recorded. Also, the recorded history values are added to the * given json value. * * @param pJmxReq request for which an entry should be added in this history store * @param pJson the JSONObject to which to add the history. */ public synchronized void updateAndAdd(JmxRequest pJmxReq, JSONObject pJson) { long timestamp = System.currentTimeMillis() / 1000; pJson.put(KEY_TIMESTAMP, timestamp); JmxRequest.Type type = pJmxReq.getType(); if (type == EXEC || type == WRITE) { HistoryEntry entry = historyStore.get(new HistoryKey(pJmxReq)); if (entry != null) { synchronized (entry) { // A history data to json object for the response pJson.put(KEY_HISTORY, entry.jsonifyValues()); // Update history for next time if (type == EXEC) { entry.add(pJson.get(KEY_VALUE), timestamp); } else if (type == WRITE) { // The new value to set as string representation entry.add(pJmxReq.getValue(), timestamp); } } } } else if (type == READ) { updateReadHistory(pJmxReq, pJson, timestamp); } }
/** Populate recent bookmarks. */ public void populateRecentBookmarks() { JMenu bookmarksMenu = this.recentBookmarksMenu; bookmarksMenu.removeAll(); Collection<HistoryEntry<BookmarkInfo>> historyEntries = BookmarksHistory.getInstance().getRecentEntries(PREFERRED_MAX_MENU_SIZE); for (HistoryEntry<BookmarkInfo> hentry : historyEntries) { BookmarkInfo binfo = hentry.getItemInfo(); String text = binfo.getTitle(); URL url = binfo.getUrl(); String urlText = url.toExternalForm(); if ((text == null) || (text.length() == 0)) { text = urlText; } long elapsed = System.currentTimeMillis() - hentry.getTimetstamp(); text = text + " (" + Timing.getElapsedText(elapsed) + " ago)"; Action action = this.actionPool.createBookmarkNavigateAction(url); JMenuItem menuItem = ComponentSource.menuItem(text, action); StringBuffer toolTipText = new StringBuffer(); toolTipText.append("<html>"); toolTipText.append(urlText); String description = binfo.getDescription(); if ((description != null) && (description.length() != 0)) { toolTipText.append("<br>"); toolTipText.append(description); } menuItem.setToolTipText(toolTipText.toString()); bookmarksMenu.add(menuItem); } }
/** Helper for {@link #get(File, Repository)}. */ private History getHistory(File file, Repository repository, boolean withFiles) throws HistoryException, SQLException { final String filePath = getSourceRootRelativePath(file); final String reposPath = toUnixPath(repository.getDirectoryName()); final ArrayList<HistoryEntry> entries = new ArrayList<HistoryEntry>(); final ConnectionResource conn = connectionManager.getConnectionResource(); try { final PreparedStatement ps; if (file.isDirectory()) { // Fetch history for all files under this directory. ps = conn.getStatement(GET_DIR_HISTORY); ps.setString(2, filePath); } else { // Fetch history for a single file only. ps = conn.getStatement(GET_FILE_HISTORY); ps.setString(2, getParentPath(filePath)); ps.setString(3, getBaseName(filePath)); } ps.setString(1, reposPath); final PreparedStatement filePS = withFiles ? conn.getStatement(GET_CS_FILES) : null; try (ResultSet rs = ps.executeQuery()) { while (rs.next()) { // Get the information about a changeset String revision = rs.getString(1); String author = rs.getString(2); Timestamp time = rs.getTimestamp(3); String message = rs.getString(4); HistoryEntry entry = new HistoryEntry(revision, time, author, null, message, true); entries.add(entry); // Fill the list of files touched by the changeset, if // requested. if (withFiles) { int changeset = rs.getInt(5); filePS.setInt(1, changeset); try (ResultSet fileRS = filePS.executeQuery()) { while (fileRS.next()) { entry.addFile(fileRS.getString(1)); } } } } } } finally { connectionManager.releaseConnection(conn); } History history = new History(); history.setHistoryEntries(entries); RuntimeEnvironment env = RuntimeEnvironment.getInstance(); if (env.isTagsEnabled() && repository.hasFileBasedTags()) { repository.assignTagsInHistory(history); } return history; }
/** * Set the global maximum limit for history entries * * @param pGlobalMaxEntries limit */ public synchronized void setGlobalMaxEntries(int pGlobalMaxEntries) { globalMaxEntries = pGlobalMaxEntries; // Refresh all entries for (HistoryEntry entry : historyStore.values()) { entry.setMaxEntries(globalMaxEntries); entry.trim(); } }
private void addAttributeFromSingleValue( JSONObject pHistMap, String pAttrName, HistoryKey pKey, Object pValue, long pTimestamp) { HistoryEntry entry = getEntry(pKey, pValue, pTimestamp); if (entry != null) { synchronized (entry) { pHistMap.put(pAttrName, entry.jsonifyValues()); entry.add(pValue, pTimestamp); } } }
/** * Remove the oldest changeset from a list (assuming sorted with most recent changeset first) and * verify that it is the changeset we expected to find there. * * @param entries a list of {@code HistoryEntry} objects * @param revision the revision we expect the oldest entry to have * @throws HistoryException if the oldest entry was not the one we expected */ void removeAndVerifyOldestChangeset(List<HistoryEntry> entries, String revision) throws HistoryException { HistoryEntry entry = entries.isEmpty() ? null : entries.remove(entries.size() - 1); // TODO We should check more thoroughly that the changeset is the one // we expected it to be, since some SCMs may change the revision // numbers so that identical revision numbers does not always mean // identical changesets. We could for example get the cached changeset // and compare more fields, like author and date. if (entry == null || !revision.equals(entry.getRevision())) { throw new HistoryException( "Cached revision '" + revision + "' not found in the repository " + getDirectoryName()); } }
private void writeComposite( final Element res, final VirtualFile file, final EditorWithProviderComposite composite, final boolean pinned, final EditorWithProviderComposite selectedEditor) { final Element fileElement = new Element("file"); fileElement.setAttribute("leaf-file-name", file.getName()); // TODO: all files final HistoryEntry entry = composite.currentStateAsHistoryEntry(); entry.writeExternal(fileElement, getManager().getProject()); fileElement.setAttribute("pinned", Boolean.toString(pinned)); fileElement.setAttribute( "current", Boolean.toString(composite.equals(getManager().getLastSelected()))); fileElement.setAttribute("current-in-tab", Boolean.toString(composite.equals(selectedEditor))); res.addContent(fileElement); }
private HistoryEntry getEntry(HistoryKey pKey, Object pValue, long pTimestamp) { HistoryEntry entry = historyStore.get(pKey); if (entry != null) { return entry; } // Now try all known patterns and add lazily the key for (HistoryKey key : patterns.keySet()) { if (key.matches(pKey)) { entry = new HistoryEntry(patterns.get(key)); entry.add(pValue, pTimestamp); historyStore.put(pKey, entry); return entry; } } return null; }
/* (non-Javadoc) * @see com.mvplite.view.NavigationController#setCurrentView(com.mvplite.view.NavigateableView) */ @Override public void setCurrentView(NavigateableView view) { if (!setCurrentViewCausedByHistoryChange) { // Add url fragmentHistory support String uriFragment = calculateUri(view); HistoryEntry entry = new HistoryEntry(); entry.eventsToFire = calculateEventsToFireList(view); if (historyStack.isEmpty()) historyStack.put("", entry); historyStack.put(uriFragment, entry); page.setUriFragment(uriFragment, false); // Seems not to work at first call } fireNavigatedTo(view); }
private void logEntries(Collection<HistoryEntry> entries) { LocalHistory.LOG.log(Level.FINE, "LocalHistory returns {0} entries", entries.size()); // NOI18N if (LocalHistory.LOG.isLoggable(Level.FINEST)) { StringBuilder sb = new StringBuilder(); Iterator<HistoryEntry> it = entries.iterator(); while (it.hasNext()) { HistoryEntry entry = it.next(); sb.append("["); // NOI18N sb.append(DateFormat.getDateTimeInstance().format(entry.getDateTime())); sb.append(",["); // NOI18N sb.append(toString(entry.getFiles())); sb.append("]]"); // NOI18N if (it.hasNext()) sb.append(","); // NOI18N } LocalHistory.LOG.finest(sb.toString()); } }
/** * Build maps from directory names and file names to their respective identifiers in the database. * The directories and files that are not already in the database, are added to it. * * @param conn the connection to the database * @param history the history to get the file and directory names from * @param reposId the id of the repository * @param dirMap a map which will be filled with directory names and ids * @param fileMap a map which will be filled with file names and ids */ private void getFilesAndDirectories( ConnectionResource conn, History history, int reposId, Map<String, Integer> dirMap, Map<String, Integer> fileMap) throws SQLException { populateFileOrDirMap(conn.getStatement(GET_DIRS), reposId, dirMap); populateFileOrDirMap(conn.getStatement(GET_FILES), reposId, fileMap); int insertCount = 0; PreparedStatement insDir = conn.getStatement(INSERT_DIR); PreparedStatement insFile = conn.getStatement(INSERT_FILE); for (HistoryEntry entry : history.getHistoryEntries()) { for (String file : entry.getFiles()) { String fullPath = toUnixPath(file); // Add the file to the database and to the map if it isn't // there already. Assumption: If the file is in the database, // all its parent directories are also there. if (!fileMap.containsKey(fullPath)) { // Get the dir id for this file, potentially adding the // parent directories to the db and to dirMap. int dir = addAllDirs(insDir, reposId, fullPath, dirMap); int fileId = nextFileId.getAndIncrement(); insFile.setInt(1, dir); insFile.setString(2, getBaseName(fullPath)); insFile.setInt(3, fileId); insFile.executeUpdate(); fileMap.put(fullPath, fileId); // Commit every now and then to allow the database to free // resources (like locks and transaction log), but not too // frequently, since that may kill the performance. It is // OK not to commit for every file added, since the worst // thing that could happen is that we need to re-insert // the files added since the last commit in case of a crash. insertCount++; if (insertCount % 30 == 0) { conn.commit(); } } } } }
@Override public ASerializedView getSerializableRepresentation() { SerializedRadialHierarchyView serializedForm = new SerializedRadialHierarchyView(this); serializedForm.setMaxDisplayedHierarchyDepth(iMaxDisplayedHierarchyDepth); serializedForm.setNewSelection(bIsNewSelection); serializedForm.setDefaultDrawingStrategyType( drawingStrategyManager.getDefaultDrawingStrategy().getDrawingStrategyType()); ADrawingState currentDrawingState = drawingController.getCurrentDrawingState(); if (pdCurrentRootElement != null) { if ((currentDrawingState.getType() == EDrawingStateType.DRAWING_STATE_DETAIL_OUTSIDE) || (currentDrawingState.getType() == EDrawingStateType.DRAWING_STATE_FULL_HIERARCHY)) { serializedForm.setDrawingStateType(currentDrawingState.getType()); serializedForm.setRootElementID(pdCurrentRootElement.getElementID()); serializedForm.setSelectedElementID(pdCurrentSelectedElement.getElementID()); serializedForm.setRootElementStartAngle(pdCurrentRootElement.getCurrentStartAngle()); serializedForm.setSelectedElementStartAngle( pdCurrentSelectedElement.getCurrentStartAngle()); } else { HistoryEntry historyEntry = navigationHistory.getCurrentHistoryEntry(); serializedForm.setDrawingStateType(historyEntry.getDrawingState().getType()); serializedForm.setRootElementID(historyEntry.getRootElement().getElementID()); serializedForm.setSelectedElementID(historyEntry.getSelectedElement().getElementID()); serializedForm.setRootElementStartAngle(historyEntry.getRootElementStartAngle()); serializedForm.setSelectedElementStartAngle(historyEntry.getSelectedElementStartAngle()); } } return serializedForm; }
/** * Configure the history length for a specific entry. If the length is 0 disable history for this * key * * @param pKey history key * @param pMaxEntries number of maximal entries. If larger than globalMaxEntries, then * globalMaxEntries is used instead. */ public synchronized void configure(HistoryKey pKey, int pMaxEntries) { int maxEntries = pMaxEntries > globalMaxEntries ? globalMaxEntries : pMaxEntries; // Remove entries if set to 0 if (pMaxEntries == 0) { removeEntries(pKey); return; } if (pKey.isMBeanPattern()) { patterns.put(pKey, maxEntries); // Trim all already stored keys for (HistoryKey key : historyStore.keySet()) { if (pKey.matches(key)) { HistoryEntry entry = historyStore.get(key); entry.setMaxEntries(maxEntries); entry.trim(); } } } else { HistoryEntry entry = historyStore.get(pKey); if (entry != null) { entry.setMaxEntries(maxEntries); entry.trim(); } else { entry = new HistoryEntry(maxEntries); historyStore.put(pKey, entry); } } }
// @Override public View getView(int inPos, View vwConvert, ViewGroup parent) { View vwView; if (vwConvert == null) { vwView = mInflater.inflate(R.layout.history_item, parent, false); } else { vwView = vwConvert; } TextView txtvExpr = (TextView) vwView.findViewById(R.id.historyExpr); TextView txtvResult = (TextView) vwView.findViewById(R.id.historyResult); HistoryEntry entry = mEntries.elementAt(inPos); String base = entry.getBase(); txtvExpr.setText(entry.getBase()); try { String strRes = mEval.evaluate(base); txtvResult.setText("= " + strRes); } catch (SyntaxException e) { txtvResult.setText(""); } return vwView; }
/** * Assign tags to changesets they represent The complete list of tags must be pre-built using * {@code getTagList()}. Then this function squeeze all tags to changesets which actually exist in * the history of given file. Must be implemented repository-specific. * * @see getTagList * @param hist History we want to assign tags to. */ void assignTagsInHistory(History hist) throws HistoryException { if (hist == null) { return; } if (this.getTagList() == null) { throw new HistoryException("Tag list was not created before assigning tags to changesets!"); } Iterator<TagEntry> it = this.getTagList().descendingIterator(); TagEntry lastTagEntry = null; // Go through all commits of given file for (HistoryEntry ent : hist.getHistoryEntries()) { // Assign all tags created since the last revision // Revision in this HistoryEntry must be already specified! // TODO is there better way to do this? We need to "repeat" // last element returned by call to next() while (lastTagEntry != null || it.hasNext()) { if (lastTagEntry == null) { lastTagEntry = it.next(); } if (lastTagEntry.compareTo(ent) >= 0) { if (ent.getTags() == null) { ent.setTags(lastTagEntry.getTags()); } else { ent.setTags(ent.getTags() + ", " + lastTagEntry.getTags()); } } else { break; } if (it.hasNext()) { lastTagEntry = it.next(); } else { lastTagEntry = null; } } } }
public View getView(int position, View convertView, ViewGroup parent) { View view; if (convertView == null) { view = mInflater.inflate(R.layout.history_item, parent, false); } else { view = convertView; } TextView expr = (TextView) view.findViewById(R.id.historyExpr); TextView result = (TextView) view.findViewById(R.id.historyResult); HistoryEntry entry = mEntries.elementAt(position); String base = entry.getBase(); expr.setText(entry.getBase()); try { String res = mEval.evaluate(base); result.setText("= " + res); } catch (SyntaxException e) { result.setText(""); } return view; }
/** * {@inheritDoc} * * @param figureId The id of the {@link Figure}. * @param clientId The id of the {@link Figure}s {@link Client owner}. * @param targetFieldNotation The {@link Field#getNotation() notation} of the {@link Field} the * {@link Figure} wants to move to. * @param simpMessagingTemplate Template for sending websocket messages. * @throws MoveNotAllowedException */ @Override public void performMovement( String figureId, String clientId, String targetFieldNotation, SimpMessagingTemplate simpMessagingTemplate) throws MoveNotAllowedException { // Only the current player is allowed to do moves. // Fixes CCD2015-50 if (!clientId.equals(getCurrentPlayer().getId())) throw new MoveNotAllowedException(); List<Hexagon> possibleMovements = getPossibleFieldsToMove(figureId); // Throw an exception when the client ID does not match the figures owner id // or when the target field is not in the list of possible moves. if (possibleMovements .stream() .filter(hexagon -> hexagon.getNotation().equals(targetFieldNotation)) .count() == 0 || getFigures() .stream() // Only figures, that are sill active. .filter(hexagonFigure -> !hexagonFigure.isRemoved()) // Only figures equals to the given id .filter(hexagonFigure -> hexagonFigure.getId().equals(figureId)) // Only the clients figures .filter(hexagonFigure -> hexagonFigure.getClient().getId().equals(clientId)) .count() == 0) throw new MoveNotAllowedException(); HistoryEntry historyEntry = new HistoryEntry(); historyEntry.setPlayer(getCurrentPlayer()); // Remove a figure from the chessboard if there is a figure on the target field getFigures() .stream() // Only figures, that are sill active. // Fixes CCD2015-52 .filter(hexagonFigure -> !hexagonFigure.isRemoved()) // Only figures on the target hexagon .filter( hexagonFigure -> hexagonFigure.getPosition().getNotation().equals(targetFieldNotation)) .findFirst() .ifPresent( hexagonFigure -> { historyEntry .getChessboardEvents() .add( new FigureEvent() .setFigureId(hexagonFigure.getId()) .setEvent(FigureEvent.Event.REMOVED)); hexagonFigure.setRemoved(true); }); // Move our figure to the target field getFigures() .stream() // Only figures, that are sill active. .filter(hexagonFigure -> !hexagonFigure.isRemoved()) // Only figures on the source hexagon .filter(hexagonFigure -> hexagonFigure.getId().equals(figureId)) .findFirst() .ifPresent( hexagonFigure -> { historyEntry .getChessboardEvents() .add( new MovementEvent() .setFigureId(figureId) .setFromNotation(hexagonFigure.getPosition().getNotation()) .setToNotation(targetFieldNotation)); try { hexagonFigure.setPosition((Hexagon) getFieldByNotation(targetFieldNotation)); } catch (NotationNotFoundException e) { logger.error("", e); } }); // Add action to history getParentGame().getGameHistory().add(historyEntry); // Send event through websocket simpMessagingTemplate.convertAndSend("/game/" + getParentGame().getId(), historyEntry); // Change the active player and send it through websocket setCurrentPlayer(getCurrentPlayer().getNextClient()); checkIfCurrentPlayerIsDefeated(); while (getCurrentPlayer().isDefeated()) { setCurrentPlayer(getCurrentPlayer().getNextClient()); checkIfCurrentPlayerIsDefeated(); } getParentGame() .getPlayerList() .stream() .filter(client -> !client.isDefeated()) .forEach( client -> { PlayerChangedEvent playerChangedEvent = new PlayerChangedEvent().setItYouTurn(client.equals(getCurrentPlayer())); simpMessagingTemplate.convertAndSend( "/game/" + getParentGame().getId() + "/" + client.getId(), playerChangedEvent); }); }
/** Test of parse method, of class ClearCaseHistoryParser. */ @Test public void parseDirHistory() throws Exception { String author1 = "First Last (username)"; String author2 = "First2 Last2 (username2)"; String output = "create directory version\n" + "20050401.162902\n" + author1 + "\n" + "/main/3\n" + "Removed directory element \"prototype\".\n" + ".\n" + "create directory version\n" + "20020618.215917\n" + author2 + "\n" + "/main/2\n" + "Merge from wwwww for dddddd\n" + ".\n" + "create directory version\n" + "20010228.174617\n" + author1 + "\n" + "/main/1\n" + "New structure.\n" + "\n" + "Added directory element \"generic\".\n" + "Added directory element \"prototype\".\n" + "Added directory element \"install\".\n" + "Added directory element \"service\".\n" + ".\n" + "create directory version\n" + "20001215.092522\n" + author2 + "\n" + "/main/0\n" + "\n" + ".\n" + "create branch\n" + "20001215.092522\n" + author1 + "\n" + "/main\n" + "\n" + ".\n" + "create directory element\n" + "20001215.092522\n" + author1 + "\n" + "\n" + "\n" + "."; History result = instance.parse(output); assertNotNull(result); assertEquals(4, result.getHistoryEntries().size()); HistoryEntry e1 = result.getHistoryEntries().get(0); assertEquals("/main/3", e1.getRevision()); assertEquals(author1, e1.getAuthor()); assertEquals(0, e1.getFiles().size()); assertTrue(e1.getMessage().contains("prototype")); HistoryEntry e4 = result.getHistoryEntries().get(3); assertEquals("/main/0", e4.getRevision()); assertEquals(author2, e4.getAuthor()); assertEquals(0, e4.getFiles().size()); }
@Override protected JPanel processFiles(@NotNull List<Element> fileElements, final JPanel context) { final Ref<EditorWindow> windowRef = new Ref<EditorWindow>(); UIUtil.invokeAndWaitIfNeeded( new Runnable() { @Override public void run() { windowRef.set(context == null ? createEditorWindow() : findWindowWith(context)); } }); final EditorWindow window = windowRef.get(); LOG.assertTrue(window != null); VirtualFile focusedFile = null; for (int i = 0; i < fileElements.size(); i++) { final Element file = fileElements.get(i); if (i == 0) { EditorTabbedContainer tabbedPane = window.getTabbedPane(); if (tabbedPane != null) { try { int limit = Integer.parseInt( file.getParentElement() .getAttributeValue( JBTabsImpl.SIDE_TABS_SIZE_LIMIT_KEY.toString(), String.valueOf(JBTabsImpl.DEFAULT_MAX_TAB_WIDTH))); UIUtil.putClientProperty( tabbedPane.getComponent(), JBTabsImpl.SIDE_TABS_SIZE_LIMIT_KEY, limit); } catch (NumberFormatException e) { // ignore } } } try { final FileEditorManagerImpl fileEditorManager = getManager(); Element historyElement = file.getChild(HistoryEntry.TAG); final HistoryEntry entry = HistoryEntry.createLight(fileEditorManager.getProject(), historyElement); final VirtualFile virtualFile = entry.getFile(); if (virtualFile == null) throw new InvalidDataException("No file exists: " + entry.getFilePointer().getUrl()); Document document = ApplicationManager.getApplication() .runReadAction( new Computable<Document>() { @Override public Document compute() { return virtualFile.isValid() ? FileDocumentManager.getInstance().getDocument(virtualFile) : null; } }); final boolean isCurrentInTab = Boolean.valueOf(file.getAttributeValue(CURRENT_IN_TAB)).booleanValue(); Boolean pin = Boolean.valueOf(file.getAttributeValue(PINNED)); fileEditorManager.openFileImpl4( window, virtualFile, entry, isCurrentInTab, isCurrentInTab, pin, i); if (isCurrentInTab) { focusedFile = virtualFile; } if (document != null) { // This is just to make sure document reference is kept on stack till this point // so that document is available for folding state deserialization in HistoryEntry // constructor // and that document will be created only once during file opening document.putUserData(DUMMY_KEY, null); } updateProgress(); } catch (InvalidDataException e) { if (ApplicationManager.getApplication().isUnitTestMode()) { LOG.error(e); } } } if (focusedFile != null) { getManager().addSelectionRecord(focusedFile, window); } return window.myPanel; }
private void storeHistory(ConnectionResource conn, History history, Repository repository) throws SQLException { Integer reposId = null; Map<String, Integer> authors = null; Map<String, Integer> files = null; Map<String, Integer> directories = null; PreparedStatement addChangeset = null; PreparedStatement addDirchange = null; PreparedStatement addFilechange = null; PreparedStatement addFilemove = null; RuntimeEnvironment env = RuntimeEnvironment.getInstance(); // return immediately when there is nothing to do List<HistoryEntry> entries = history.getHistoryEntries(); if (entries.isEmpty()) { return; } for (int i = 0; ; i++) { try { if (reposId == null) { reposId = getRepositoryId(conn, repository); conn.commit(); } if (authors == null) { authors = getAuthors(conn, history, reposId); conn.commit(); } if (directories == null || files == null) { Map<String, Integer> dirs = new HashMap<String, Integer>(); Map<String, Integer> fls = new HashMap<String, Integer>(); getFilesAndDirectories(conn, history, reposId, dirs, fls); conn.commit(); directories = dirs; files = fls; } if (addChangeset == null) { addChangeset = conn.getStatement(ADD_CHANGESET); } if (addDirchange == null) { addDirchange = conn.getStatement(ADD_DIRCHANGE); } if (addFilechange == null) { addFilechange = conn.getStatement(ADD_FILECHANGE); } if (addFilemove == null) { addFilemove = conn.getStatement(ADD_FILEMOVE); } // Success! Break out of the loop. break; } catch (SQLException sqle) { handleSQLException(sqle, i); conn.rollback(); } } addChangeset.setInt(1, reposId); // getHistoryEntries() returns the entries in reverse chronological // order, but we want to insert them in chronological order so that // their auto-generated identity column can be used as a chronological // ordering column. Otherwise, incremental updates will make the // identity column unusable for chronological ordering. So therefore // we walk the list backwards. for (ListIterator<HistoryEntry> it = entries.listIterator(entries.size()); it.hasPrevious(); ) { HistoryEntry entry = it.previous(); retry: for (int i = 0; ; i++) { try { addChangeset.setString(2, entry.getRevision()); addChangeset.setInt(3, authors.get(entry.getAuthor())); addChangeset.setTimestamp(4, new Timestamp(entry.getDate().getTime())); String msg = entry.getMessage(); // Truncate the message if it can't fit in a VARCHAR // (bug #11663). if (msg.length() > MAX_MESSAGE_LENGTH) { msg = truncate(msg, MAX_MESSAGE_LENGTH); } addChangeset.setString(5, msg); int changesetId = nextChangesetId.getAndIncrement(); addChangeset.setInt(6, changesetId); addChangeset.executeUpdate(); // Add one row for each file in FILECHANGES, and one row // for each path element of the directories in DIRCHANGES. Set<String> addedDirs = new HashSet<String>(); addDirchange.setInt(1, changesetId); addFilechange.setInt(1, changesetId); for (String file : entry.getFiles()) { // ignore ignored files String repodir = ""; try { repodir = env.getPathRelativeToSourceRoot(new File(repository.getDirectoryName()), 0); } catch (IOException ex) { Logger.getLogger(JDBCHistoryCache.class.getName()).log(Level.SEVERE, null, ex); } String fullPath = toUnixPath(file); if (!history.isIgnored(file.substring(repodir.length() + 1))) { int fileId = files.get(fullPath); addFilechange.setInt(2, fileId); addFilechange.executeUpdate(); } String[] pathElts = splitPath(fullPath); for (int j = 0; j < pathElts.length; j++) { String dir = unsplitPath(pathElts, j); // Only add to DIRCHANGES if we haven't already // added this dir/changeset combination. if (!addedDirs.contains(dir)) { addDirchange.setInt(2, directories.get(dir)); addDirchange.executeUpdate(); addedDirs.add(dir); } } } conn.commit(); // Successfully added the entry. Break out of retry loop. break retry; } catch (SQLException sqle) { handleSQLException(sqle, i); conn.rollback(); } } } /* * Special handling for certain files - this is mainly for files which * have been renamed in Mercurial repository. * This ensures that their complete history (follow) will be saved. */ for (String filename : history.getIgnoredFiles()) { String file_path = repository.getDirectoryName() + File.separatorChar + filename; File file = new File(file_path); String repo_path = file_path.substring(env.getSourceRootPath().length()); History hist; try { hist = repository.getHistory(file); } catch (HistoryException ex) { Logger.getLogger(JDBCHistoryCache.class.getName()).log(Level.SEVERE, null, ex); continue; } int fileId = files.get(repo_path); for (HistoryEntry entry : hist.getHistoryEntries()) { retry: for (int i = 0; ; i++) { try { int changesetId = getIdForRevision(entry.getRevision()); /* * If the file exists in the changeset, store it in * the table tracking moves of the file when it had * one of its precedent names so it can be found * when performing historyget on directory. */ if (entry.getFiles().contains(repo_path)) { addFilechange.setInt(1, changesetId); addFilechange.setInt(2, fileId); addFilechange.executeUpdate(); } else { addFilemove.setInt(1, changesetId); addFilemove.setInt(2, fileId); addFilemove.executeUpdate(); } conn.commit(); break retry; } catch (SQLException sqle) { handleSQLException(sqle, i); conn.rollback(); } } } } }
/** Test of parse method, of class ClearCaseHistoryParser. */ @Test public void parseFileHistory() throws Exception { String author1 = "First Last (username)"; String author2 = "First2 Last2 (username2)"; String output = "create version\n" + "20020618.212343\n" + author1 + "\n" + "/main/3\n" + "Merge from eeeee for ffffff\n" + ".\n" + "create version\n" + "20020222.164239\n" + author2 + "\n" + "/main/2\n" + "Merge from projper branch.\n" + "Adding aaaaaaa to the yyyyy.\n" + ".\n" + "create version\n" + "20020208.150825\n" + author2 + "\n" + "/main/1\n" + "Target for javac set to 1.3.\n" + "Fixed handling of " + " res directory.\n" + ".\n" + "create version\n" + "20010924.095104\n" + author2 + "\n" + "/main/0\n" + "\n" + ".\n" + "create branch\n" + "20010924.095104\n" + author2 + "\n" + "/main\n" + "\n" + ".\n" + "create file element\n" + "20010924.095104\n" + author1 + "\n" + "\n" + "\n" + "."; History result = instance.parse(output); assertNotNull(result); assertEquals(4, result.getHistoryEntries().size()); HistoryEntry e1 = result.getHistoryEntries().get(0); assertEquals("/main/3", e1.getRevision()); assertEquals(author1, e1.getAuthor()); assertEquals(0, e1.getFiles().size()); assertTrue(e1.getMessage().contains("eeeee")); HistoryEntry e4 = result.getHistoryEntries().get(3); assertEquals("/main/0", e4.getRevision()); assertEquals(author2, e4.getAuthor()); assertEquals(0, e4.getFiles().size()); }