diff --git a/src/components/ProposalForm/ProposalForm.jsx b/src/components/ProposalForm/ProposalForm.jsx
index 6ed2ba264..a76e98bbe 100644
--- a/src/components/ProposalForm/ProposalForm.jsx
+++ b/src/components/ProposalForm/ProposalForm.jsx
@@ -22,6 +22,7 @@ import ModalMDGuide from "src/components/ModalMDGuide";
import DraftSaver from "./DraftSaver";
import { useProposalForm } from "./hooks";
import usePolicy from "src/hooks/api/usePolicy";
+import { isAnchoring } from "src/helpers";
import {
PROPOSAL_TYPE_REGULAR,
PROPOSAL_TYPE_RFP,
@@ -262,6 +263,11 @@ const ProposalFormWrapper = ({
const handleSubmit = useCallback(
async (values, { resetForm, setSubmitting, setFieldError }) => {
try {
+ if (isAnchoring()) {
+ throw new Error(
+ "Submitting proposals is temporarily unavailable while a daily censorship resistance routine is in progress. Sorry for the inconvenience. This will be fixed soon. Check back in 10 minutes."
+ );
+ }
const { type, rfpLink, ...others } = values;
if (type === PROPOSAL_TYPE_RFP_SUBMISSION) {
const rfpWithVoteSummaries = (await onFetchProposalsBatchWithoutState(
diff --git a/src/containers/Comments/Comment/CommentWrapper.jsx b/src/containers/Comments/Comment/CommentWrapper.jsx
index 3453d7807..e1d9d2808 100644
--- a/src/containers/Comments/Comment/CommentWrapper.jsx
+++ b/src/containers/Comments/Comment/CommentWrapper.jsx
@@ -4,6 +4,7 @@ import CommentForm from "src/components/CommentForm/CommentFormLazy";
import Link from "src/components/Link";
import { useComment } from "../hooks";
import Comment from "./Comment";
+import { handleCommentSubmission } from "../helpers";
const ContextLink = React.memo(({ parentid, recordToken, recordType }) => (
{
- return onSubmitComment({
- comment,
- token,
- parentID: commentid
- });
- },
- [token, commentid, onSubmitComment]
+ handleCommentSubmission(onSubmitComment, token, commentid),
+ [onSubmitComment, token, commentid]
);
const handleCommentSubmitted = useCallback(() => {
diff --git a/src/containers/Comments/Comments.jsx b/src/containers/Comments/Comments.jsx
index 3f1e5777f..b0c3ba7c0 100644
--- a/src/containers/Comments/Comments.jsx
+++ b/src/containers/Comments/Comments.jsx
@@ -22,6 +22,7 @@ import {
createSelectOptionFromSortOption,
commentSortOptions,
handleCommentCensoringInfo,
+ handleCommentSubmission,
NUMBER_OF_LIST_PLACEHOLDERS
} from "./helpers";
import useIdentity from "src/hooks/api/useIdentity";
@@ -36,10 +37,6 @@ import useLocalStorage from "src/hooks/utils/useLocalStorage";
const COMMENTS_LOGIN_MODAL_ID = "commentsLoginModal";
-// Anchoring issue ref: see https://github.com/decred/politeiagui/issues/1941
-const TEMP_ANCHORING_MINUTE = 58;
-const ANCHORING_TIMEOUT_MS = 5 * 60 * 1000; // 5' in ms
-
const Comments = ({
numOfComments,
recordToken,
@@ -93,15 +90,10 @@ const Comments = ({
const paywallMissing = paywallEnabled && !isPaid;
const isSingleThread = !!threadParentID;
- const handleSubmitComment = useCallback(
- (comment) => {
- return onSubmitComment({
- comment,
- token: recordToken,
- parentID: 0
- });
- },
- [recordToken, onSubmitComment]
+ const handleSubmitComment = handleCommentSubmission(
+ onSubmitComment,
+ recordToken,
+ 0
);
const handleSetSortOption = useCallback(
@@ -213,42 +205,6 @@ const Comments = ({
((comments && !comments.find((c) => c.commentid === threadParentID)) ||
numOfComments === 0);
- // Temporarily block comments due to git anchoring: See https://github.com/decred/politeiagui/issues/1941
- const getTimeLeftToAnchor = () => {
- const date = new Date();
- const timeLeft =
- TEMP_ANCHORING_MINUTE * 60000 -
- date.getMinutes() * 60000 -
- date.getSeconds() * 1000 -
- date.getMilliseconds();
- return timeLeft;
- };
-
- const [isAnchoring, setIsAchoring] = useState(getTimeLeftToAnchor() <= 0);
- const handleToggleAnchoring = useCallback(() => {
- setIsAchoring(!isAnchoring);
- }, [setIsAchoring, isAnchoring]);
-
- useEffect(
- function anchoringModeListener() {
- let timeout = null;
- if (isAnchoring) {
- timeout = setTimeout(handleToggleAnchoring, ANCHORING_TIMEOUT_MS);
- }
- return () => timeout && clearTimeout(timeout);
- },
- [isAnchoring, handleToggleAnchoring]
- );
- useEffect(
- function commentsAllowedListener() {
- let timeout = null;
- if (!isAnchoring) {
- timeout = setTimeout(handleToggleAnchoring, getTimeLeftToAnchor());
- }
- return () => timeout && clearTimeout(timeout);
- },
- [isAnchoring, handleToggleAnchoring]
- );
return (
<>
)}
- {isAnchoring && (
-
- Commenting temporarily unavailable while an hourly censorship
- resistance routine is in progress. Sorry for the
- inconvenience. This will be fixed soon. Check back in 5
- minutes.
-
- )}
{!readOnly && !!identityError && }
{!isSingleThread && !readOnly && (
)}
diff --git a/src/containers/Comments/helpers.js b/src/containers/Comments/helpers.js
index 7bf28286b..f0483d38d 100644
--- a/src/containers/Comments/helpers.js
+++ b/src/containers/Comments/helpers.js
@@ -1,4 +1,5 @@
import orderBy from "lodash/fp/orderBy";
+import { isAnchoring } from "src/helpers";
export const NUMBER_OF_LIST_PLACEHOLDERS = 3;
@@ -63,3 +64,18 @@ export function handleCommentCensoringInfo(cb, ...args) {
cb(...args, reason);
};
}
+
+export function handleCommentSubmission(cb, token, parentID = 0) {
+ return (comment) => {
+ if (isAnchoring()) {
+ throw new Error(
+ "Commenting temporarily unavailable while a daily censorship resistance routine is in progress. Sorry for the inconvenience. This will be fixed soon. Check back in 10 minutes."
+ );
+ }
+ return cb({
+ comment,
+ token,
+ parentID
+ });
+ };
+}
diff --git a/src/helpers.js b/src/helpers.js
index 2dd52aa52..f67a5a77f 100644
--- a/src/helpers.js
+++ b/src/helpers.js
@@ -447,3 +447,29 @@ export const fromUSDCentsToUSDUnits = (cents) =>
export const fromUSDUnitsToUSDCents = (units) => parseInt(units * 100, 10);
export const isEmpty = (obj) => Object.keys(obj).length === 0;
+
+/** Pure function that given 2 UNIX timestamps returns the differnce between them in minutes */
+export const getTimeDiffInMinutes = (d1, d2) => {
+ return (d1 - d2) / 60e3;
+};
+
+/** This is a temporary fix to prevent comments and proposals submissions during anchoring time */
+/**
+ * @function isAnchoring
+ * @param {string} anchoringStartTime UTC time to prevent submissions in HH:MM format
+ * @param {number} anchoringDuration Duration in minutes
+ */
+export const isAnchoring = (
+ anchoringStartTime = "06:58",
+ anchoringDuration = 10
+) => {
+ const targetDate = new Date();
+ const [startHour, startMinute] = anchoringStartTime.split(":");
+ targetDate.setUTCHours(startHour);
+ targetDate.setUTCMinutes(startMinute);
+ const timeDiffMinutes = getTimeDiffInMinutes(
+ new Date().getTime(),
+ targetDate.getTime()
+ );
+ return timeDiffMinutes >= 0 && timeDiffMinutes < anchoringDuration;
+};
diff --git a/src/pages/User/VerifyKey/VerifyKey.jsx b/src/pages/User/VerifyKey/VerifyKey.jsx
index 835040f59..e4e686609 100644
--- a/src/pages/User/VerifyKey/VerifyKey.jsx
+++ b/src/pages/User/VerifyKey/VerifyKey.jsx
@@ -50,7 +50,9 @@ const VerifyKey = ({ location, history }) => {
const success = verifyUserKey && verifyUserKey.success;
const error = verifyUserKeyError;
const pushToHome = useCallback(() => history.push("/"), [history]);
- const successButtonText = (isCMS ? "Ok, go to invoices" : "Ok, go to proposals");
+ const successButtonText = isCMS
+ ? "Ok, go to invoices"
+ : "Ok, go to proposals";
return (
diff --git a/src/tests/helpers.test.js b/src/tests/helpers.test.js
index f12026ba5..c4092ff0d 100644
--- a/src/tests/helpers.test.js
+++ b/src/tests/helpers.test.js
@@ -31,3 +31,29 @@ describe("test helpers functions", () => {
);
});
});
+
+describe("test getTimeDiffInMinutes function", () => {
+ test("it should return 0 when d2 == d1", () => {
+ expect(help.getTimeDiffInMinutes(1591030381, 1591030381)).toEqual(0);
+ });
+
+ test("it should return positive when d1 > d2", () => {
+ expect(
+ help.getTimeDiffInMinutes(1591030521000, 1591030381000)
+ ).toBeGreaterThan(0);
+ });
+
+ test("it should return negative when d1 < d2", () => {
+ expect(
+ help.getTimeDiffInMinutes(1591030381000, 1591030700000)
+ ).toBeLessThan(0);
+ });
+
+ test("it should return correctly within the same hour", () => {
+ expect(help.getTimeDiffInMinutes(1591030200000, 1591029900000)).toEqual(5);
+ });
+
+ test("it should return correctly when the hour overflows", () => {
+ expect(help.getTimeDiffInMinutes(1591031100000, 1591030500000)).toEqual(10);
+ });
+});